提交 4d0a7347 编写于 作者: Z zegezy

“组件”插件

上级 25fa9d08
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>org.ssssssss</groupId>
<artifactId>magic-api-plugins</artifactId>
<version>2.0.1</version>
<relativePath/>
</parent>
<artifactId>magic-api-plugin-component</artifactId>
<packaging>jar</packaging>
<name>magic-api-plugin-component</name>
<description>magic-api-plugin-component</description>
<build>
<plugins>
<!-- npm install && npm run build -->
<plugin>
<groupId>org.codehaus.mojo</groupId>
<artifactId>exec-maven-plugin</artifactId>
<version>1.6.0</version>
<executions>
<execution>
<id>exec-npm-install</id>
<phase>generate-resources</phase>
<goals>
<goal>exec</goal>
</goals>
<configuration>
<executable>npm</executable>
<arguments>
<argument>install</argument>
</arguments>
<workingDirectory>${basedir}/src/console</workingDirectory>
</configuration>
</execution>
<execution>
<id>exec-npm-run-build</id>
<phase>generate-resources</phase>
<goals>
<goal>exec</goal>
</goals>
<configuration>
<executable>npm</executable>
<arguments>
<argument>run</argument>
<argument>build</argument>
</arguments>
<workingDirectory>${basedir}/src/console</workingDirectory>
</configuration>
</execution>
</executions>
</plugin>
<plugin>
<artifactId>maven-resources-plugin</artifactId>
<version>3.2.0</version>
<executions>
<execution>
<id>copy-resource</id>
<phase>generate-resources</phase>
<goals>
<goal>copy-resources</goal>
</goals>
<configuration>
<outputDirectory>${basedir}/target/classes/magic-editor/plugins</outputDirectory>
<resources>
<resource>
<directory>${basedir}/src/console/dist</directory>
</resource>
</resources>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
{
"name": "magic-component",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
"build": "vite build"
},
"author": "",
"license": "ISC",
"devDependencies": {
"vue": "^3.2.31",
"@vitejs/plugin-vue": "^2.2.4",
"vite-plugin-svg-icons": "^1.1.0",
"vite": "^2.8.6"
}
}
<template>
<div class="magic-component-info">
<form>
<label>{{ $i('component.form.name') }}</label>
<magic-input v-model:value="info.name" :placeholder="$i('component.form.placeholder.name')" width="250px"/>
<label>{{ $i('component.form.path') }}</label>
<magic-input v-model:value="info.path" :placeholder="$i('component.form.placeholder.path')" width="auto" style="flex:1"/>
</form>
<div style="flex:1;padding-top:5px;">
<magic-textarea v-model:value="info.description" :placeholder="$i('component.form.placeholder.description')"/>
</div>
</div>
</template>
<script setup>
import { inject } from 'vue'
const $i = inject('i18n.format')
const info = inject('info')
</script>
<style scoped>
.magic-component-info{
display: flex;
flex-direction: column;
flex: 1;
padding: 5px;
}
.magic-component-info form{
display: flex;
}
.magic-component-info form label{
display: inline-block;
width: 75px;
height: 22px;
line-height: 22px;
font-weight: 400;
text-align: right;
padding: 0 5px;
}
.magic-component-info form :deep(.magic-textarea){
margin: 5px;
}
</style>
export default {
component: {
title: 'Component Info',
name: 'Component',
form: {
name: 'Component Name',
path: 'Component Path',
description: 'Component Description',
placeholder: {
name: 'Please Enter Component Name',
path: 'Please Enter Component Path',
description: 'Please Enter Component Description'
}
}
},
}
export default {
component: {
title: '组件信息',
name: '组件',
form: {
name: '组件名称',
path: '组件路径',
description: '组件描述',
placeholder: {
name: '请输入组件名称',
path: '请输入组件路径',
description: '请输入组件描述'
}
}
}
}
<?xml version="1.0" standalone="no"?><!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd"><svg t="1647853515880" class="icon" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="1190" xmlns:xlink="http://www.w3.org/1999/xlink" width="200" height="200"><defs><style type="text/css">@font-face { font-family: feedback-iconfont; src: url("//at.alicdn.com/t/font_1031158_u69w8yhxdu.woff2?t=1630033759944") format("woff2"), url("//at.alicdn.com/t/font_1031158_u69w8yhxdu.woff?t=1630033759944") format("woff"), url("//at.alicdn.com/t/font_1031158_u69w8yhxdu.ttf?t=1630033759944") format("truetype"); }
</style></defs><path d="M914.5 653.5c-5.5 0-11 1.1-16 3.3l-0.2 0.1h-0.2L510.2 822.2 122.2 657h-0.2l-0.2-0.1c-5-2.1-10.3-3.3-16-3.3-23.1 0-41.8 19.3-41.8 43.1 0 18 10.7 33.3 25.8 39.8l403.9 172.1 0.4 0.1c10.2 4.4 21.8 4.4 32 0l0.2-0.1c0.1 0 0.1-0.1 0.2-0.1l403.9-172.1c15.1-6.5 25.8-21.8 25.8-39.8 0.1-23.8-18.6-43.1-41.7-43.1z m0-186.5c-7.9-0.2-16 3.2-16 3.2L510.2 635.6 121.8 470.2s-10.3-3.2-16-3.2C82.7 467 64 486.2 64 510c0 17.9 10.7 33.3 25.8 39.7l403.9 172c0.1 0 0.1 0.1 0.2 0.1l0.1 0.1c5 2.1 10.3 3.3 16 3.3 5.7 0 11.1-1.2 16-3.3l0.2-0.1c0.1 0 0.1 0 0.2-0.1l403.9-172c15.1-6.4 25.8-21.8 25.9-39.7 0.1-23.8-18.6-43-41.7-43zM89.8 363.2l403.9 172.1c0.1 0 0.1 0 0.2 0.1l0.1 0.1c5 2.1 10.3 3.2 16 3.2 5.5 0 10.9-1.1 16-3.2l0.2-0.1 0.2-0.1 403.9-172c15.1-6.5 25.8-21.8 25.9-39.7 0-18-10.7-33.3-25.8-39.8L526.5 111.6c-0.1 0-0.1 0-0.2-0.1l-0.2-0.1c-10.2-4.4-21.8-4.4-32 0l-0.1 0.1L89.8 283.7C74.7 290.1 64 305.5 64 323.5c0 17.9 10.7 33.2 25.8 39.7z" p-id="1191" fill="#000000"></path></svg>
\ No newline at end of file
import MagicComponent from './service/magic-component.js'
import localZhCN from './i18n/zh-cn.js'
import localEn from './i18n/en.js'
import MagicComponentInfo from './components/magic-component-info.vue'
import 'vite-plugin-svg-icons/register'
export default (opt) => {
const i18n = opt.i18n
// 添加i18n 国际化信息
i18n.add('zh-cn', localZhCN)
i18n.add('en', localEn)
return {
// 左侧资源
resource: [{
// 资源类型,和后端存储结构一致
type: 'component',
// 展示图标
icon: '#magic-component-component', // #开头表示图标在插件中
// 展示名称
title: 'component.name',
// 运行服务
service: MagicComponent(opt.bus, opt.constants, i18n.format, opt.Message, opt.request),
}],
// 底部工具条
toolbars: [{
// 当打开的资源类型为 task 时显示
type: 'component',
// 工具条展示的标题
title: 'component.title',
// 展示图标
icon: 'parameter',
// 对应的组件
component: MagicComponentInfo,
}]
}
}
export default function (bus, constants, $i, Message, request) {
return {
// svg text
getIcon: item => ['Vue', '#41B883'],
// 任务名称
name: $i('component.name'),
// 脚本语言
language: 'html',
// 默认脚本
defaultScript: `<template>
</template>
<script setup>
</script>
<style scoped>
</style>`,
// 是否允许执行测试
runnable: false,
// 是否需要填写路径
requirePath: true,
// 合并
merge: item => item
}
}
import vue from '@vitejs/plugin-vue'
import viteSvgIcons from 'vite-plugin-svg-icons'
import path from 'path'
import pkg from './package.json'
export default {
base: './',
build: {
minify: false,
cssCodeSplit: true, // 将组件的 style 打包到 js 文件中
outDir: 'dist',
lib: {
target: 'esnext',
formats: ['iife'],
entry: path.resolve(__dirname, 'src/index.js'),
name: 'MagicComponent',
fileName: (format) => `magic-component.${pkg.version}.${format}.js`
},
rollupOptions: {
// 确保外部化处理那些你不想打包进库的依赖
external: ['vue'],
output: {
// 在 UMD 构建模式下为这些外部化的依赖提供一个全局变量
globals: {
vue: 'Vue'
}
}
}
},
plugins: [
vue(),
viteSvgIcons({
iconDirs: [path.resolve(process.cwd(), 'src/icons')],
symbolId: 'magic-component-[name]'
}),
]
}
package org.ssssssss.magicapi.component.model;
import org.ssssssss.magicapi.core.model.MagicEntity;
import org.ssssssss.magicapi.core.model.PathMagicEntity;
import java.util.Objects;
public class ComponentInfo extends PathMagicEntity {
/**
* 组件描述
*/
private String description;
public String getDescription() {
return description;
}
public void setDescription(String description) {
this.description = description;
}
public ComponentInfo copy() {
ComponentInfo info = new ComponentInfo();
super.copyTo(info);
info.setDescription(this.description);
return info;
}
@Override
public MagicEntity simple() {
ComponentInfo info = new ComponentInfo();
super.simple(info);
return info;
}
@Override
public boolean equals(Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
if (!super.equals(o)) return false;
ComponentInfo componentInfo = (ComponentInfo) o;
return Objects.equals(id, componentInfo.id) &&
Objects.equals(path, componentInfo.path) &&
Objects.equals(script, componentInfo.script) &&
Objects.equals(name, componentInfo.name) &&
Objects.equals(description, componentInfo.description);
}
@Override
public int hashCode() {
return Objects.hash(id, path, script, name, groupId, description);
}
}
package org.ssssssss.magicapi.component.service;
import org.ssssssss.magicapi.component.model.ComponentInfo;
import org.ssssssss.magicapi.core.exception.InvalidArgumentException;
import org.ssssssss.magicapi.core.model.JsonCode;
import org.ssssssss.magicapi.core.service.AbstractPathMagicResourceStorage;
import java.util.UUID;
public class ComponentInfoMagicResourceStorage extends AbstractPathMagicResourceStorage<ComponentInfo> {
@Override
public String folder() {
return "component";
}
@Override
public Class<ComponentInfo> magicClass() {
return ComponentInfo.class;
}
@Override
public void validate(ComponentInfo entity) {
}
@Override
public String buildMappingKey(ComponentInfo info) {
return buildMappingKey(info, magicResourceService.getGroupPath(info.getGroupId()));
}
@Override
public boolean requirePath() {
return false;
}
}
package org.ssssssss.magicapi.component.service;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.context.event.EventListener;
import org.ssssssss.magicapi.component.model.ComponentInfo;
import org.ssssssss.magicapi.core.event.FileEvent;
import org.ssssssss.magicapi.core.event.GroupEvent;
import org.ssssssss.magicapi.core.service.AbstractMagicDynamicRegistry;
import org.ssssssss.magicapi.core.service.MagicResourceStorage;
public class ComponentMagicDynamicRegistry extends AbstractMagicDynamicRegistry<ComponentInfo> {
public ComponentMagicDynamicRegistry(MagicResourceStorage<ComponentInfo> magicResourceStorage) {
super(magicResourceStorage);
}
@EventListener(condition = "#event.type == 'component'")
public void onFileEvent(FileEvent event) {
processEvent(event);
}
@EventListener(condition = "#event.type == 'component'")
public void onGroupEvent(GroupEvent event) {
processEvent(event);
}
}
package org.ssssssss.magicapi.component.starter;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.ssssssss.magicapi.component.service.ComponentInfoMagicResourceStorage;
import org.ssssssss.magicapi.component.service.ComponentMagicDynamicRegistry;
import org.ssssssss.magicapi.core.config.MagicPluginConfiguration;
import org.ssssssss.magicapi.core.model.Plugin;
@Configuration
public class MagicAPIComponentConfiguration implements MagicPluginConfiguration {
@Bean
@ConditionalOnMissingBean
public ComponentInfoMagicResourceStorage componentInfoMagicResourceStorage() {
return new ComponentInfoMagicResourceStorage();
}
@Bean
@ConditionalOnMissingBean
public ComponentMagicDynamicRegistry componentMagicDynamicRegistry(ComponentInfoMagicResourceStorage componentInfoMagicResourceStorage) {
return new ComponentMagicDynamicRegistry(componentInfoMagicResourceStorage);
}
@Override
public Plugin plugin() {
return new Plugin("组件", "MagicComponent", "magic-component.1.0.0.iife.js");
}
}
org.springframework.boot.autoconfigure.EnableAutoConfiguration=org.ssssssss.magicapi.component.starter.MagicAPIComponentConfiguration
......@@ -15,6 +15,7 @@
<description>auto generate http api</description>
<modules>
<module>magic-api-plugin-task</module>
<module>magic-api-plugin-component</module>
<module>magic-api-plugin-swagger</module>
<module>magic-api-plugin-redis</module>
<module>magic-api-plugin-mongo</module>
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册