diff --git a/muyu-modules/muyu-data-source/muyu-data-source-access-client/pom.xml b/muyu-modules/muyu-data-source/muyu-data-source-access-client/pom.xml
new file mode 100644
index 0000000..89453bb
--- /dev/null
+++ b/muyu-modules/muyu-data-source/muyu-data-source-access-client/pom.xml
@@ -0,0 +1,20 @@
+
+
+ 4.0.0
+
+ com.muyu
+ muyu-data-source
+ 3.6.3
+
+
+ muyu-data-source-access-client
+
+
+ 17
+ 17
+ UTF-8
+
+
+
diff --git a/muyu-modules/muyu-data-source/muyu-data-source-access-server/pom.xml b/muyu-modules/muyu-data-source/muyu-data-source-access-server/pom.xml
new file mode 100644
index 0000000..d86d87f
--- /dev/null
+++ b/muyu-modules/muyu-data-source/muyu-data-source-access-server/pom.xml
@@ -0,0 +1,20 @@
+
+
+ 4.0.0
+
+ com.muyu
+ muyu-data-source
+ 3.6.3
+
+
+ muyu-data-source-access-server
+
+
+ 17
+ 17
+ UTF-8
+
+
+
diff --git a/muyu-modules/muyu-data-source/pom.xml b/muyu-modules/muyu-data-source/pom.xml
index b2bb493..4278d74 100644
--- a/muyu-modules/muyu-data-source/pom.xml
+++ b/muyu-modules/muyu-data-source/pom.xml
@@ -15,6 +15,8 @@
muyu-data-source-common
muyu-data-source-remote
muyu-data-source-server
+ muyu-data-source-access-server
+ muyu-data-source-access-client
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/Engineversion.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/Engineversion.java
new file mode 100644
index 0000000..4f403fa
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/Engineversion.java
@@ -0,0 +1,69 @@
+package com.muyu.ruleengine.domain;
+
+import com.muyu.ruleengine.domain.req.EngineversionEditReq;
+import com.muyu.ruleengine.domain.req.EngineversionSaveReq;
+import lombok.AllArgsConstructor;
+import lombok.Builder;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+/**
+ * 引擎维护对象 EngineVersion
+ *
+ * @author DeKangLiu
+ * on 2024/5/7
+ */
+@Data
+@Builder
+@NoArgsConstructor
+@AllArgsConstructor
+public class Engineversion {
+ /**引擎维护id*/
+ private Long id;
+
+ /**规则引擎id*/
+ private Integer ruleId;
+
+ /**版本编码*/
+ private String versionCode;
+
+ /**版本名称*/
+ private String name;
+
+ /**版本code*/
+ private String code;
+
+ /**是否激活*/
+ private String isActivate;
+
+ /**状态*/
+ private String status;
+
+ /**描述*/
+ private String description;
+
+ /**引擎描述*/
+ private String codeIng;
+
+ /**是否测试*/
+ private String isTest;
+
+ /**
+ * 修改构造器
+ */
+ public static Engineversion editBuild( EngineversionEditReq engineversionEditReq)
+ {
+ return Engineversion.builder()
+ .id(engineversionEditReq.getId())
+ .ruleId(engineversionEditReq.getRuleId())
+ .versionCode(engineversionEditReq.getVersionCode())
+ .name(engineversionEditReq.getName())
+ .code(engineversionEditReq.getCode())
+ .isActivate(engineversionEditReq.getIsActivate())
+ .status(engineversionEditReq.getStatus())
+ .description(engineversionEditReq.getDescription())
+ .codeIng(engineversionEditReq.getCodeIng())
+ .build();
+ }
+
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/Ruleengine.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/Ruleengine.java
new file mode 100644
index 0000000..39d5adf
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/Ruleengine.java
@@ -0,0 +1,142 @@
+package com.muyu.ruleengine.domain;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.NoArgsConstructor;
+import lombok.AllArgsConstructor;
+import lombok.experimental.SuperBuilder;
+import io.swagger.annotations.*;
+import com.muyu.common.core.annotation.Excel;
+import com.muyu.ruleengine.domain.req.RuleengineQueryReq;
+import com.muyu.ruleengine.domain.req.RuleengineSaveReq;
+import com.muyu.ruleengine.domain.req.RuleengineEditReq;
+import com.muyu.common.core.web.domain.BaseEntity;
+
+import java.util.List;
+
+/**
+ * 规则引擎对象 ruleengine
+ *
+ * @author WangLei
+ * @date 2024-04-24
+ */
+@Data
+@SuperBuilder
+@NoArgsConstructor
+@AllArgsConstructor
+@TableName("ruleengine")
+@EqualsAndHashCode(callSuper = true)
+@ApiModel(value = "Ruleengine", description = "规则引擎")
+public class Ruleengine extends BaseEntity {
+
+ private static final long serialVersionUID = 1L;
+
+ /** */
+ @TableId(value = "id",type = IdType.AUTO)
+ @ApiModelProperty(name = "", value = "")
+ private Long id;
+
+ /** 规则名称 */
+ @Excel(name = "规则名称")
+ @ApiModelProperty(name = "规则名称", value = "规则名称")
+ private String name;
+
+ /** 引擎编码 */
+ @Excel(name = "引擎编码")
+ @ApiModelProperty(name = "引擎编码", value = "引擎编码")
+ private String code;
+
+ /** 规则类型 */
+ @Excel(name = "规则类型")
+ @ApiModelProperty(name = "规则类型", value = "规则类型")
+ private String type;
+
+ /** 规则作用域 */
+ @Excel(name = "规则作用域")
+ @ApiModelProperty(name = "规则作用域", value = "规则作用域")
+ private String level;
+
+
+ /** 是否激活 */
+ @Excel(name = "是否激活")
+ @ApiModelProperty(name = "是否激活", value = "是否激活")
+ private String isActivate;
+
+ /** 规则状态 */
+ @Excel(name = "规则状态")
+ @ApiModelProperty(name = "规则状态", value = "规则状态")
+ private String status;
+
+ /** 规则描述 */
+ @Excel(name = "规则描述")
+ @ApiModelProperty(name = "规则描述", value = "规则描述")
+ private String description;
+
+ /** 备注 */
+ @Excel(name = "备注")
+ @ApiModelProperty(name = "备注", value = "备注")
+ private String remark;
+
+ /** 规则描述 */
+ @Excel(name = "编码")
+ @ApiModelProperty(name = "编码", value = "编码")
+ private String engineCode;
+
+
+
+
+ /**
+ * 查询构造器
+ */
+ public static Ruleengine queryBuild( RuleengineQueryReq ruleengineQueryReq){
+ return Ruleengine.builder()
+ .name(ruleengineQueryReq.getName())
+ .code(ruleengineQueryReq.getCode())
+ .type(ruleengineQueryReq.getType())
+ .level(ruleengineQueryReq.getLevel())
+ .isActivate(ruleengineQueryReq.getIsActivate())
+ .status(ruleengineQueryReq.getStatus())
+ .description(ruleengineQueryReq.getDescription())
+ .remark(ruleengineQueryReq.getRemark())
+ .build();
+ }
+
+ /**
+ * 添加构造器
+ */
+ public static Ruleengine saveBuild(RuleengineSaveReq ruleengineSaveReq){
+ return Ruleengine.builder()
+ .name(ruleengineSaveReq.getName())
+ .code(ruleengineSaveReq.getCode())
+ .type(ruleengineSaveReq.getType())
+ .level(ruleengineSaveReq.getLevel())
+ .isActivate(ruleengineSaveReq.getIsActivate())
+ .status(ruleengineSaveReq.getStatus())
+ .description(ruleengineSaveReq.getDescription())
+ .remark(ruleengineSaveReq.getRemark())
+ .engineCode(ruleengineSaveReq.getEngineCode())
+ .build();
+ }
+
+ /**
+ * 修改构造器
+ */
+ public static Ruleengine editBuild(Long id, RuleengineEditReq ruleengineEditReq){
+ return Ruleengine.builder()
+ .id(id)
+ .name(ruleengineEditReq.getName())
+ .code(ruleengineEditReq.getCode())
+ .type(ruleengineEditReq.getType())
+ .level(ruleengineEditReq.getLevel())
+ .isActivate(ruleengineEditReq.getIsActivate())
+ .status(ruleengineEditReq.getStatus())
+ .description(ruleengineEditReq.getDescription())
+ .remark(ruleengineEditReq.getRemark())
+ .engineCode(ruleengineEditReq.getEngineCode())
+ .build();
+ }
+
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/model/RuleContentModel.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/model/RuleContentModel.java
new file mode 100644
index 0000000..f6e2cc5
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/model/RuleContentModel.java
@@ -0,0 +1,29 @@
+package com.muyu.ruleengine.domain.model;
+
+import lombok.AllArgsConstructor;
+import lombok.Builder;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+/**
+ * RuleContentModel
+ *
+ * @author WangLei
+ * @Date 2024/5/2 002 14:27
+ */
+@Data
+@Builder
+@AllArgsConstructor
+@NoArgsConstructor
+public class RuleContentModel {
+
+ private Long id;
+ /**
+ * 规则id
+ */
+ private Long ruleId;
+ /**
+ * 规则内容
+ */
+ private String ruleContent;
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/model/RuleengineModel.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/model/RuleengineModel.java
new file mode 100644
index 0000000..bce1615
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/model/RuleengineModel.java
@@ -0,0 +1,145 @@
+package com.muyu.ruleengine.domain.model;
+
+import com.baomidou.mybatisplus.annotation.IdType;
+import com.baomidou.mybatisplus.annotation.TableId;
+import com.baomidou.mybatisplus.annotation.TableName;
+import com.muyu.common.core.annotation.Excel;
+import com.muyu.common.core.web.domain.BaseEntity;
+import com.muyu.ruleengine.domain.Engineversion;
+import com.muyu.ruleengine.domain.req.RuleengineEditReq;
+import com.muyu.ruleengine.domain.req.RuleengineQueryReq;
+import com.muyu.ruleengine.domain.req.RuleengineSaveReq;
+import io.swagger.annotations.ApiModel;
+import io.swagger.annotations.ApiModelProperty;
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.NoArgsConstructor;
+import lombok.experimental.SuperBuilder;
+
+import java.util.List;
+
+/**
+ * 规则引擎对象 ruleengine
+ *
+ * @author WangLei
+ * @date 2024-04-24
+ */
+@Data
+@SuperBuilder
+@NoArgsConstructor
+@AllArgsConstructor
+@TableName("ruleengine")
+@EqualsAndHashCode(callSuper = true)
+@ApiModel(value = "Ruleengine", description = "规则引擎")
+public class RuleengineModel extends BaseEntity {
+
+ private static final long serialVersionUID = 1L;
+
+ /** */
+ @TableId(value = "id",type = IdType.AUTO)
+ @ApiModelProperty(name = "", value = "")
+ private Long id;
+
+ /** 规则名称 */
+ @Excel(name = "规则名称")
+ @ApiModelProperty(name = "规则名称", value = "规则名称")
+ private String name;
+
+ /** 引擎编码 */
+ @Excel(name = "引擎编码")
+ @ApiModelProperty(name = "引擎编码", value = "引擎编码")
+ private String code;
+
+ /** 规则类型 */
+ @Excel(name = "规则类型")
+ @ApiModelProperty(name = "规则类型", value = "规则类型")
+ private String type;
+
+ /** 规则作用域 */
+ @Excel(name = "规则作用域")
+ @ApiModelProperty(name = "规则作用域", value = "规则作用域")
+ private String level;
+
+
+ /** 是否激活 */
+ @Excel(name = "是否激活")
+ @ApiModelProperty(name = "是否激活", value = "是否激活")
+ private String isActivate;
+
+ /** 规则状态 */
+ @Excel(name = "规则状态")
+ @ApiModelProperty(name = "规则状态", value = "规则状态")
+ private String status;
+
+ /** 规则描述 */
+ @Excel(name = "规则描述")
+ @ApiModelProperty(name = "规则描述", value = "规则描述")
+ private String description;
+
+ /** 备注 */
+ @Excel(name = "备注")
+ @ApiModelProperty(name = "备注", value = "备注")
+ private String remark;
+
+ /** 规则描述 */
+ @Excel(name = "编码")
+ @ApiModelProperty(name = "编码", value = "编码")
+ private String engineCode;
+
+ /**引擎维护对象*/
+ private List engineversionList;
+
+
+ /**
+ * 查询构造器
+ */
+ public static RuleengineModel queryBuild(RuleengineQueryReq ruleengineQueryReq){
+ return RuleengineModel.builder()
+ .name(ruleengineQueryReq.getName())
+ .code(ruleengineQueryReq.getCode())
+ .type(ruleengineQueryReq.getType())
+ .level(ruleengineQueryReq.getLevel())
+ .isActivate(ruleengineQueryReq.getIsActivate())
+ .status(ruleengineQueryReq.getStatus())
+ .description(ruleengineQueryReq.getDescription())
+ .remark(ruleengineQueryReq.getRemark())
+ .build();
+ }
+
+ /**
+ * 添加构造器
+ */
+ public static RuleengineModel saveBuild(RuleengineSaveReq ruleengineSaveReq){
+ return RuleengineModel.builder()
+ .name(ruleengineSaveReq.getName())
+ .code(ruleengineSaveReq.getCode())
+ .type(ruleengineSaveReq.getType())
+ .level(ruleengineSaveReq.getLevel())
+ .isActivate(ruleengineSaveReq.getIsActivate())
+ .status(ruleengineSaveReq.getStatus())
+ .description(ruleengineSaveReq.getDescription())
+ .remark(ruleengineSaveReq.getRemark())
+ .engineCode(ruleengineSaveReq.getEngineCode())
+ .build();
+ }
+
+ /**
+ * 修改构造器
+ */
+ public static RuleengineModel editBuild(Long id, RuleengineEditReq ruleengineEditReq){
+ return RuleengineModel.builder()
+ .id(id)
+ .name(ruleengineEditReq.getName())
+ .code(ruleengineEditReq.getCode())
+ .type(ruleengineEditReq.getType())
+ .level(ruleengineEditReq.getLevel())
+ .isActivate(ruleengineEditReq.getIsActivate())
+ .status(ruleengineEditReq.getStatus())
+ .description(ruleengineEditReq.getDescription())
+ .remark(ruleengineEditReq.getRemark())
+ .engineCode(ruleengineEditReq.getEngineCode())
+ .build();
+ }
+
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/EngineversionEditReq.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/EngineversionEditReq.java
new file mode 100644
index 0000000..c9ba27a
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/EngineversionEditReq.java
@@ -0,0 +1,45 @@
+package com.muyu.ruleengine.domain.req;
+
+import lombok.AllArgsConstructor;
+import lombok.Builder;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+
+/**
+ * 引擎维护对象修改 EngineVersionEditReq
+ *
+ * @author DeKangLiu
+ * Date 2024/5/7 15:07
+ */
+@Data
+@Builder
+@NoArgsConstructor
+@AllArgsConstructor
+public class EngineversionEditReq {
+ /**引擎维护id*/
+ private Long id;
+
+ /**规则引擎id*/
+ private Integer ruleId;
+
+ /**版本编码*/
+ private String versionCode;
+
+ /**版本名称*/
+ private String name;
+
+ /**版本code*/
+ private String code;
+
+ /**是否激活*/
+ private String isActivate;
+
+ /**状态*/
+ private String status;
+
+ /**描述*/
+ private String description;
+
+ /**引擎描述*/
+ private String codeIng;
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/EngineversionSaveReq.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/EngineversionSaveReq.java
new file mode 100644
index 0000000..ddcd478
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/EngineversionSaveReq.java
@@ -0,0 +1,45 @@
+package com.muyu.ruleengine.domain.req;
+
+import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.NoArgsConstructor;
+import lombok.experimental.SuperBuilder;
+
+/**
+ * 引擎维护对象添加 EngineversionSaveReq
+ *
+ * @author DeKangLiu
+ * Date 2024/5/7 18:34
+ */
+@Data
+@SuperBuilder
+@NoArgsConstructor
+@AllArgsConstructor
+public class EngineversionSaveReq {
+ /**规则引擎id*/
+ private Integer ruleId;
+
+ /**版本编码*/
+ private String versionCode;
+
+ /**版本名称*/
+ private String name;
+
+ /**规则引擎内容*/
+ private String code;
+
+ /**是否激活*/
+ private String isActivate;
+
+ /**状态*/
+ private String status;
+
+ /**备注*/
+ private String description;
+
+ /**引擎描述*/
+ private String codeIng;
+
+ /**是否测试*/
+ private String isTest;
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleContentReq.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleContentReq.java
new file mode 100644
index 0000000..f3b24c5
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleContentReq.java
@@ -0,0 +1,16 @@
+package com.muyu.ruleengine.domain.req;
+
+import lombok.Data;
+
+/**
+ * RuleContentReq
+ *
+ * @author WangLei
+ * @Date 2024/5/2 002 14:30
+ */
+@Data
+public class RuleContentReq {
+
+ private Long ruleId;
+ private String ruleContent;
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleengineEditReq.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleengineEditReq.java
new file mode 100644
index 0000000..430fa81
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleengineEditReq.java
@@ -0,0 +1,65 @@
+package com.muyu.ruleengine.domain.req;
+
+import com.muyu.common.core.annotation.Excel;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.NoArgsConstructor;
+import lombok.AllArgsConstructor;
+import lombok.experimental.SuperBuilder;
+import io.swagger.annotations.*;
+import com.muyu.common.core.web.domain.BaseEntity;
+
+/**
+ * 规则引擎对象 ruleengine
+ *
+ * @author WangLei
+ * @date 2024-04-24
+ */
+@Data
+@SuperBuilder
+@NoArgsConstructor
+@AllArgsConstructor
+@ApiModel(value = "RuleengineEditReq", description = "规则引擎")
+public class RuleengineEditReq extends BaseEntity {
+
+ private static final long serialVersionUID = 1L;
+
+ /** 规则名称 */
+ @ApiModelProperty(name = "规则名称", value = "规则名称")
+ private String name;
+ /** 引擎编码 */
+ @Excel(name = "引擎编码")
+ @ApiModelProperty(name = "引擎编码", value = "引擎编码")
+ private String code;
+
+ /** 规则类型 */
+ @ApiModelProperty(name = "规则类型", value = "规则类型")
+ private String type;
+
+ /** 规则作用域 */
+ @Excel(name = "规则作用域")
+ @ApiModelProperty(name = "规则作用域", value = "规则作用域")
+ private String level;
+ /** 是否激活 */
+ @ApiModelProperty(name = "是否激活", value = "是否激活")
+ private String isActivate;
+
+ /** 规则状态 */
+ @ApiModelProperty(name = "规则状态", value = "规则状态")
+ private String status;
+
+ /** 规则描述 */
+ @ApiModelProperty(name = "规则描述", value = "规则描述")
+ private String description;
+
+ /** 备注 */
+ @Excel(name = "备注")
+ @ApiModelProperty(name = "备注", value = "备注")
+ private String remark;
+
+ /** 编码 */
+ @Excel(name = "编码")
+ @ApiModelProperty(name = "编码", value = "编码")
+ private String engineCode;
+
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleengineQueryReq.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleengineQueryReq.java
new file mode 100644
index 0000000..d3cec62
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleengineQueryReq.java
@@ -0,0 +1,59 @@
+package com.muyu.ruleengine.domain.req;
+
+import com.muyu.common.core.annotation.Excel;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.NoArgsConstructor;
+import lombok.AllArgsConstructor;
+import lombok.experimental.SuperBuilder;
+import io.swagger.annotations.*;
+import com.muyu.common.core.web.domain.BaseEntity;
+
+/**
+ * 规则引擎对象 ruleengine
+ *
+ * @author WangLei
+ * @date 2024-04-24
+ */
+@Data
+@SuperBuilder
+@NoArgsConstructor
+@AllArgsConstructor
+@ApiModel(value = "RuleengineQueryReq", description = "规则引擎")
+public class RuleengineQueryReq extends BaseEntity {
+
+ private static final long serialVersionUID = 1L;
+
+ /** 规则名称 */
+ @ApiModelProperty(name = "规则名称", value = "规则名称")
+ private String name;
+ /** 引擎编码 */
+ @Excel(name = "引擎编码")
+ @ApiModelProperty(name = "引擎编码", value = "引擎编码")
+ private String code;
+
+ /** 规则类型 */
+ @ApiModelProperty(name = "规则类型", value = "规则类型")
+ private String type;
+
+ /** 规则作用域 */
+ @Excel(name = "规则作用域")
+ @ApiModelProperty(name = "规则作用域", value = "规则作用域")
+ private String level;
+ /** 是否激活 */
+ @ApiModelProperty(name = "是否激活", value = "是否激活")
+ private String isActivate;
+
+ /** 规则状态 */
+ @ApiModelProperty(name = "规则状态", value = "规则状态")
+ private String status;
+
+ /** 规则描述 */
+ @ApiModelProperty(name = "规则描述", value = "规则描述")
+ private String description;
+
+ /** 备注 */
+ @Excel(name = "备注")
+ @ApiModelProperty(name = "备注", value = "备注")
+ private String remark;
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleengineSaveReq.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleengineSaveReq.java
new file mode 100644
index 0000000..2f1fc8f
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-common/src/main/java/com/muyu/ruleengine/domain/req/RuleengineSaveReq.java
@@ -0,0 +1,75 @@
+package com.muyu.ruleengine.domain.req;
+
+import com.muyu.common.core.annotation.Excel;
+import lombok.Data;
+import lombok.EqualsAndHashCode;
+import lombok.NoArgsConstructor;
+import lombok.AllArgsConstructor;
+import lombok.experimental.SuperBuilder;
+import io.swagger.annotations.*;
+import com.muyu.common.core.web.domain.BaseEntity;
+
+/**
+ * 规则引擎对象 ruleengine
+ *
+ * @author WangLei
+ * @date 2024-04-24
+ */
+@Data
+@SuperBuilder
+@NoArgsConstructor
+@AllArgsConstructor
+@ApiModel(value = "RuleengineSaveReq", description = "规则引擎")
+public class RuleengineSaveReq extends BaseEntity {
+
+ private static final long serialVersionUID = 1L;
+
+ /** */
+
+ @ApiModelProperty(name = "", value = "")
+ private Long id;
+
+ /** 规则名称 */
+
+ @ApiModelProperty(name = "规则名称", value = "规则名称")
+ private String name;
+ /** 引擎编码 */
+ @Excel(name = "引擎编码")
+ @ApiModelProperty(name = "引擎编码", value = "引擎编码")
+ private String code;
+
+ /** 规则类型 */
+
+ @ApiModelProperty(name = "规则类型", value = "规则类型")
+ private String type;
+
+ /** 规则作用域 */
+ @Excel(name = "规则作用域")
+ @ApiModelProperty(name = "规则作用域", value = "规则作用域")
+ private String level;
+ /** 是否激活 */
+
+ @ApiModelProperty(name = "是否激活", value = "是否激活")
+ private String isActivate;
+
+ /** 规则状态 */
+
+ @ApiModelProperty(name = "规则状态", value = "规则状态")
+ private String status;
+
+ /** 规则描述 */
+
+ @ApiModelProperty(name = "规则描述", value = "规则描述")
+ private String description;
+ /** 备注 */
+
+ @Excel(name = "备注")
+ @ApiModelProperty(name = "备注", value = "备注")
+ private String remark;
+
+ /** 编码 */
+ @Excel(name = "编码")
+ @ApiModelProperty(name = "编码", value = "编码")
+ private String engineCode;
+
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/controller/RuleengineController.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/controller/RuleengineController.java
new file mode 100644
index 0000000..0b41773
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/controller/RuleengineController.java
@@ -0,0 +1,151 @@
+package com.muyu.ruleengine.controller;
+
+import java.util.List;
+import javax.servlet.http.HttpServletResponse;
+
+import com.muyu.ruleengine.domain.Engineversion;
+import com.muyu.ruleengine.domain.model.RuleContentModel;
+import com.muyu.ruleengine.domain.req.*;
+import io.swagger.annotations.*;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.web.bind.annotation.*;
+import com.muyu.common.core.domain.Result;
+import com.muyu.common.core.utils.poi.ExcelUtil;
+import com.muyu.common.core.web.controller.BaseController;
+import com.muyu.common.log.annotation.Log;
+import com.muyu.common.log.enums.BusinessType;
+import com.muyu.common.security.annotation.RequiresPermissions;
+import com.muyu.ruleengine.domain.Ruleengine;
+import com.muyu.ruleengine.service.RuleengineService;
+import com.muyu.common.core.web.page.TableDataInfo;
+
+/**
+ * 规则引擎Controller
+ *
+ * @author WangLei
+ * @date 2024-04-24
+ */
+@Api(tags = "规则引擎")
+@RestController
+@RequestMapping("/ruleengine")
+public class RuleengineController extends BaseController {
+ @Autowired
+ private RuleengineService ruleengineService;
+
+
+ /**
+ * 编译
+ * @param ruleContentReq 输入的内容
+ */
+ @PostMapping("/compiler")
+ public Result compiler(@RequestBody RuleContentReq ruleContentReq) {
+ return ruleengineService.compiler(ruleContentReq);
+ }
+
+ @GetMapping("/loader")
+ public Result loader() {
+ return ruleengineService.loader();
+ }
+
+
+
+ @GetMapping("/getRuleContent")
+ public Result getRuleContent(@RequestParam Long ruleId) {
+ return ruleengineService.getRuleContent(ruleId);
+ }
+
+
+ /**
+ * 查询规则引擎列表
+ */
+ @ApiOperation("获取规则引擎列表")
+ @RequiresPermissions("ruleengine:ruleengine:list")
+ @GetMapping("/list")
+ public Result> list(RuleengineQueryReq ruleengineQueryReq) {
+ startPage();
+ List list = ruleengineService.list(Ruleengine.queryBuild(ruleengineQueryReq));
+ return getDataTable(list);
+ }
+
+ /**
+ * 导出规则引擎列表
+ */
+ @ApiOperation("导出规则引擎列表")
+ @RequiresPermissions("ruleengine:ruleengine:export")
+ @Log(title = "规则引擎", businessType = BusinessType.EXPORT)
+ @PostMapping("/export")
+ public void export(HttpServletResponse response, Ruleengine ruleengine) {
+ List list = ruleengineService.list(ruleengine);
+ ExcelUtil util = new ExcelUtil(Ruleengine.class);
+ util.exportExcel(response, list, "规则引擎数据");
+ }
+
+ /**
+ * 获取规则引擎详细信息
+ */
+ @ApiOperation("获取规则引擎详细信息")
+ @RequiresPermissions("ruleengine:ruleengine:query")
+ @GetMapping(value = "/{id}")
+ @ApiImplicitParam(name = "id", value = "id", required = true, dataType = "Long", paramType = "path", dataTypeClass = Long.class)
+ public Result getInfo(@PathVariable("id") Long id) {
+ return Result.success(ruleengineService.getById(id));
+ }
+
+ /**
+ * 新增规则引擎
+ */
+ @RequiresPermissions("ruleengine:ruleengine:add")
+ @Log(title = "规则引擎", businessType = BusinessType.INSERT)
+ @PostMapping
+ @ApiOperation("新增规则引擎")
+ public Result add(@RequestBody RuleengineSaveReq ruleengineSaveReq) {
+ return toAjax(ruleengineService.save(Ruleengine.saveBuild(ruleengineSaveReq)));
+ }
+
+ /**
+ * 修改规则引擎
+ */
+ @RequiresPermissions("ruleengine:ruleengine:edit")
+ @Log(title = "规则引擎", businessType = BusinessType.UPDATE)
+ @PutMapping("/{id}")
+ @ApiOperation("修改规则引擎")
+ public Result edit(@PathVariable Long id, @RequestBody RuleengineEditReq ruleengineEditReq) {
+ return toAjax(ruleengineService.updateById(Ruleengine.editBuild(id,ruleengineEditReq)));
+ }
+
+ /**
+ * 删除规则引擎
+ */
+ @RequiresPermissions("ruleengine:ruleengine:remove")
+ @Log(title = "规则引擎", businessType = BusinessType.DELETE)
+ @DeleteMapping("/{ids}")
+ @ApiOperation("删除规则引擎")
+ @ApiImplicitParam(name = "id", value = "id", required = true, dataType = "Long", paramType = "path", dataTypeClass = String.class, example = "1,2,3,4")
+ public Result remove(@PathVariable List ids) {
+ return toAjax(ruleengineService.removeBatchByIds(ids));
+ }
+ @PostMapping("/findRuleEngineById")
+ public Result findRuleEngineById(@RequestParam Long id) {
+ return ruleengineService.findRuleEngineById(id);
+ }
+
+ @PostMapping("/addEngineversion")
+ public Result addEngineversion(@RequestBody Engineversion engineversion) {
+ return ruleengineService.addEngineversion(engineversion);
+ }
+
+ @PostMapping("/updateRuleActivate")
+ public Result updateRuleActivate(@RequestBody Ruleengine ruleengine) {
+ return ruleengineService.updateRuleActivate(ruleengine);
+ }
+
+ @PostMapping("/updateRuleStatus")
+ public Result updateRuleStatus(@RequestBody Ruleengine ruleengine) {
+ return ruleengineService.updateRuleStatus(ruleengine);
+ }
+
+ @PostMapping("/updateEngineCodeIng")
+ public Result updateEngineCodeIng(@RequestBody Engineversion engineversion) {
+ return ruleengineService.updateEngineCodeIng(engineversion);
+ }
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/mapper/RuleengineMapper.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/mapper/RuleengineMapper.java
new file mode 100644
index 0000000..bc2aa9f
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/mapper/RuleengineMapper.java
@@ -0,0 +1,37 @@
+package com.muyu.ruleengine.mapper;
+
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+import com.muyu.ruleengine.domain.Engineversion;
+import com.muyu.ruleengine.domain.Ruleengine;
+import com.muyu.ruleengine.domain.model.RuleContentModel;
+import com.muyu.ruleengine.domain.model.RuleengineModel;
+import com.muyu.ruleengine.domain.req.RuleContentReq;
+import org.apache.ibatis.annotations.Param;
+
+import java.util.List;
+
+/**
+ * 规则引擎Mapper接口
+ *
+ * @author WangLei
+ * @date 2024-04-24
+ */
+public interface RuleengineMapper extends BaseMapper {
+
+ void addRulecontent(@Param("ruleContentReq") RuleContentReq ruleContentReq);
+
+ RuleContentModel getRuleContent(@Param("ruleId") Long ruleId);
+
+ RuleengineModel findRuleEngineById(@Param("id") Long id);
+
+ List findEngineversionList(@Param("id") Long id);
+
+ void addEngineversion(Engineversion engineversion);
+
+
+ void updateRuleStatus(Ruleengine ruleengine);
+
+ void updateRuleActivate(Ruleengine ruleengine);
+
+ void updateEngineCodeIng(Engineversion engineversion);
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/service/RuleengineService.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/service/RuleengineService.java
new file mode 100644
index 0000000..e819005
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/service/RuleengineService.java
@@ -0,0 +1,42 @@
+package com.muyu.ruleengine.service;
+
+import java.util.List;
+
+import com.muyu.common.core.domain.Result;
+import com.muyu.ruleengine.domain.Engineversion;
+import com.muyu.ruleengine.domain.Ruleengine;
+import com.baomidou.mybatisplus.extension.service.IService;
+import com.muyu.ruleengine.domain.model.RuleContentModel;
+import com.muyu.ruleengine.domain.req.RuleContentReq;
+
+/**
+ * 规则引擎Service接口
+ *
+ * @author WangLei
+ * @date 2024-04-24
+ */
+public interface RuleengineService extends IService {
+ /**
+ * 查询规则引擎列表
+ *
+ * @param ruleengine 规则引擎
+ * @return 规则引擎集合
+ */
+ public List list(Ruleengine ruleengine);
+
+ Result compiler(RuleContentReq ruleContentReq);
+
+ Result loader();
+
+ Result getRuleContent(Long ruleId);
+
+ Result findRuleEngineById(Long id);
+
+ Result addEngineversion(Engineversion engineversion);
+
+ Result updateRuleActivate(Ruleengine ruleengine);
+
+ Result updateRuleStatus(Ruleengine ruleengine);
+
+ Result updateEngineCodeIng(Engineversion engineversion);
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/service/impl/RuleengineServiceImpl.java b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/service/impl/RuleengineServiceImpl.java
new file mode 100644
index 0000000..3d23994
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/java/com/muyu/ruleengine/service/impl/RuleengineServiceImpl.java
@@ -0,0 +1,222 @@
+package com.muyu.ruleengine.service.impl;
+
+import java.lang.reflect.Method;
+import java.net.URI;
+import java.nio.file.Files;
+import java.nio.file.Paths;
+import java.util.Arrays;
+import java.util.List;
+
+import com.muyu.common.core.domain.Result;
+import com.muyu.common.core.utils.ObjUtils;
+import com.muyu.ruleengine.domain.Engineversion;
+import com.muyu.ruleengine.domain.model.RuleContentModel;
+import com.muyu.ruleengine.domain.model.RuleengineModel;
+import com.muyu.ruleengine.domain.req.RuleContentReq;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Service;
+import com.muyu.ruleengine.mapper.RuleengineMapper;
+import com.muyu.ruleengine.domain.Ruleengine;
+import com.muyu.ruleengine.service.RuleengineService;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import org.springframework.web.bind.annotation.RequestBody;
+
+import javax.tools.*;
+
+/**
+ * 规则引擎Service业务层处理
+ *
+ * @author WangLei
+ * @date 2024-04-24
+ */
+@Slf4j
+@Service
+public class RuleengineServiceImpl extends ServiceImpl implements RuleengineService {
+
+
+ @Autowired
+ private RuleengineMapper ruleengineMapper;
+
+ /**
+ * 查询规则引擎列表
+ *
+ * @param ruleengine 规则引擎
+ * @return 规则引擎
+ */
+ @Override
+ public List list(Ruleengine ruleengine) {
+ LambdaQueryWrapper queryWrapper = new LambdaQueryWrapper<>();
+
+
+ if (ObjUtils.notNull(ruleengine.getName())){
+ queryWrapper.like(Ruleengine::getName, ruleengine.getName());
+ }
+
+ if (ObjUtils.notNull(ruleengine.getType())){
+ queryWrapper.eq(Ruleengine::getType, ruleengine.getType());
+ }
+
+ if (ObjUtils.notNull(ruleengine.getIsActivate())){
+ queryWrapper.eq(Ruleengine::getIsActivate, ruleengine.getIsActivate());
+ }
+
+ if (ObjUtils.notNull(ruleengine.getStatus())){
+ queryWrapper.eq(Ruleengine::getStatus, ruleengine.getStatus());
+ }
+ if (ObjUtils.notNull(ruleengine.getRemark())){
+ queryWrapper.eq(Ruleengine::getRemark, ruleengine.getRemark());
+ }
+
+ if (ObjUtils.notNull(ruleengine.getDescription())){
+ queryWrapper.eq(Ruleengine::getDescription, ruleengine.getDescription());
+ }
+
+ if (ObjUtils.notNull(ruleengine.getCreateBy())){
+ queryWrapper.eq(Ruleengine::getCreateBy, ruleengine.getCreateBy());
+ }
+
+ if (ObjUtils.notNull(ruleengine.getCreateTime())){
+ queryWrapper.eq(Ruleengine::getCreateTime, ruleengine.getCreateTime());
+ }
+
+ if (ObjUtils.notNull(ruleengine.getUpdateBy())){
+ queryWrapper.eq(Ruleengine::getUpdateBy, ruleengine.getUpdateBy());
+ }
+
+ if (ObjUtils.notNull(ruleengine.getUpdateTime())){
+ queryWrapper.eq(Ruleengine::getUpdateTime, ruleengine.getUpdateTime());
+ }
+ return list(queryWrapper);
+ }
+
+ Long ruleId=0L;
+ @Override
+ public Result compiler(RuleContentReq ruleContentReq) {
+ ruleId = ruleContentReq.getRuleId();
+ String content = ruleContentReq.getRuleContent();
+ // 指定输出目录
+ String targetDirectory = "D:\\上海专高\\专高六\\test\\muyu-modules\\muyu-ruleengine\\muyu-ruleengine-server\\target\\classes\\com\\muyu\\ruleengine\\controller";
+
+ JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
+ try (StandardJavaFileManager fileManager = compiler.getStandardFileManager(null, null, null)) {
+ // 创建一个内存中的源文件
+ JavaFileObject sourceFileObject = new JavaSourceFromString("Test"+ruleId, content);
+
+ // 编译选项
+ Iterable options = Arrays.asList("-d", targetDirectory);
+
+ // 编译源代码
+ JavaCompiler.CompilationTask task = compiler.getTask(null, fileManager, null, options, null, Arrays.asList(sourceFileObject));
+ boolean success = task.call();
+
+ if (success) {
+ ruleengineMapper.addRulecontent(ruleContentReq);
+ System.out.println("编译成功");
+ } else {
+ System.out.println("编译失败");
+ }
+
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+ return Result.success("编译成功");
+ }
+
+ @Override
+ public Result loader() {
+ try {
+ // 假设我们有一个名为com.example.MyClass的类文件
+ // 注意:这里应该是.class文件的路径
+ String classPath = "D:\\work\\2108A(3)\\cloud-server\\muyu-modules\\muyu-ruleengine\\muyu-ruleengine-server\\src\\main\\java\\com\\muyu\\ruleengine\\controller\\RuleengineController"+ruleId+".class";
+ // 读取类文件
+ byte[] classData = Files.readAllBytes(Paths.get(classPath));
+
+ // 提取类名(不包括.class和路径)
+ String className = classPath.substring(classPath.lastIndexOf('\\') + 1).replace(".class", "");
+
+ // 使用自定义类加载器加载类
+ MyClassLoader classLoader = new MyClassLoader();
+ Class> clazz = classLoader.defineClassFromBytes(className, classData);
+
+ // 使用反射创建实例并调用方法
+ Object instance = clazz.getDeclaredConstructor().newInstance();
+ Method execute = clazz.getMethod("execute", String.class);
+ System.out.println(execute.invoke(instance, "zhangsan"));
+ System.out.println(execute.invoke(instance, ""));
+ // ... 调用方法等操作
+
+ } catch (Exception e) {
+ e.printStackTrace();
+ }
+
+ return Result.success("加载成功");
+ }
+
+ @Override
+ public Result getRuleContent(Long ruleId) {
+ if (ObjUtils.notNull(ruleId)){
+ RuleContentModel ruleContentModel=ruleengineMapper.getRuleContent(ruleId);
+ return Result.success(ruleContentModel);
+ }
+ return null;
+ }
+
+ @Override
+ public Result findRuleEngineById(Long id) {
+ RuleengineModel ruleengine=ruleengineMapper.findRuleEngineById(id);
+ List engineversionList=ruleengineMapper.findEngineversionList(id);
+ ruleengine.setEngineversionList(engineversionList);
+ return Result.success(ruleengine);
+ }
+
+ @Override
+ public Result addEngineversion(Engineversion engineversion) {
+ ruleengineMapper.addEngineversion(engineversion);
+ return Result.success("成功");
+ }
+
+ @Override
+ public Result updateRuleActivate( Ruleengine ruleengine) {
+ ruleengineMapper.updateRuleActivate(ruleengine);
+ return Result.success("引擎激活状态修改成功");
+ }
+
+ @Override
+ public Result updateRuleStatus(Ruleengine ruleengine) {
+ ruleengineMapper.updateRuleStatus(ruleengine);
+ return Result.success("引擎状态修改成功");
+ }
+
+ @Override
+ public Result updateEngineCodeIng(Engineversion engineversion) {
+ ruleengineMapper.updateEngineCodeIng(engineversion);
+ return Result.success("编码保存成功");
+ }
+
+
+ public static class MyClassLoader extends ClassLoader {
+ public Class> defineClassFromBytes(String name, byte[] data) {
+ return defineClass(name, data, 0, data.length);
+ }
+ }
+ private static Iterable compilerOptions(String classOutputPath) {
+ return Arrays.asList("-d", classOutputPath);
+ }
+
+ // 辅助类:表示内存中的源文件
+ static class JavaSourceFromString extends SimpleJavaFileObject {
+ final String code;
+
+ JavaSourceFromString(String name, String code) {
+ super(URI.create("string:///" + name.replace('.', '/') + Kind.SOURCE.extension), Kind.SOURCE);
+ this.code = code;
+ }
+
+ @Override
+ public CharSequence getCharContent(boolean ignoreEncodingErrors) {
+ return code;
+ }
+ }
+}
diff --git a/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/resources/mapper/ruleengine/RuleengineMapper.xml b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/resources/mapper/ruleengine/RuleengineMapper.xml
new file mode 100644
index 0000000..ff1f036
--- /dev/null
+++ b/muyu-modules/muyu-ruleengine/muyu-ruleengine-server/src/main/resources/mapper/ruleengine/RuleengineMapper.xml
@@ -0,0 +1,55 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ select id, name,code, type,level, is_activate, status, remark,description, create_by, create_time, update_by, update_time from ruleengine
+
+
+ insert into rulecontent
+ (rule_id,rule_content)
+ values(#{ruleContentReq.ruleId},#{ruleContentReq.ruleContent})
+
+
+ insert into engineversion
+ ( rule_id, version_code, name, is_activate, status, description, code, codeIng)
+ values
+ (#{ruleId},#{versionCode},#{name},#{isActivate},#{status},#{description},#{code},#{codeIng})
+
+
+ update ruleengine set status = #{status} where id = #{id}
+
+
+ update ruleengine set is_activate = #{isActivate} where id = #{id}
+
+
+ update engineversion set codeIng = #{codeIng} ,is_test="1" where id = #{id}
+
+
+
+
+
diff --git a/muyu-modules/muyu-system/src/main/java/com/muyu/system/service/impl/SysConfigServiceImpl.java b/muyu-modules/muyu-system/src/main/java/com/muyu/system/service/impl/SysConfigServiceImpl.java
index bc07cc8..306ab03 100644
--- a/muyu-modules/muyu-system/src/main/java/com/muyu/system/service/impl/SysConfigServiceImpl.java
+++ b/muyu-modules/muyu-system/src/main/java/com/muyu/system/service/impl/SysConfigServiceImpl.java
@@ -50,6 +50,7 @@ public class SysConfigServiceImpl extends ServiceImpl