初步实现插件机制

This commit is contained in:
mxd
2022-01-22 22:40:39 +08:00
parent e6578fc3b3
commit 5710801fda
75 changed files with 985 additions and 469 deletions

View File

@@ -0,0 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns="http://maven.apache.org/POM/4.0.0"
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.0-alpha.2</version>
</parent>
<artifactId>magic-api-plugin-mongo</artifactId>
<packaging>jar</packaging>
<name>magic-api-plugin-mongo</name>
<description>magic-api-plugin-mongo</description>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-mongodb</artifactId>
</dependency>
</dependencies>
</project>

View File

@@ -0,0 +1,31 @@
package org.ssssssss.magicapi.mongo;
import com.mongodb.client.FindIterable;
import com.mongodb.client.MongoCollection;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.ssssssss.magicapi.core.config.MagicPluginConfiguration;
import org.ssssssss.magicapi.core.model.Plugin;
import org.ssssssss.script.reflection.JavaReflection;
@Configuration
public class MagicMongoConfiguration implements MagicPluginConfiguration {
@Override
public Plugin plugin() {
return new Plugin("Mongo");
}
/**
* 注入mongo模块
*/
@Bean
@ConditionalOnMissingBean
public MongoModule mongoFunctions(MongoTemplate mongoTemplate) {
JavaReflection.registerMethodExtension(MongoCollection.class, new MongoCollectionExtension());
JavaReflection.registerMethodExtension(FindIterable.class, new MongoFindIterableExtension());
return new MongoModule(mongoTemplate);
}
}

View File

@@ -0,0 +1,93 @@
package org.ssssssss.magicapi.mongo;
import com.mongodb.client.FindIterable;
import com.mongodb.client.MongoCollection;
import com.mongodb.client.model.UpdateOptions;
import org.bson.Document;
import org.ssssssss.script.annotation.Comment;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
/**
* MongoCollection方法扩展
*
* @author mxd
*/
public class MongoCollectionExtension {
@Comment("执行批量插入操作")
public void insert(MongoCollection<Document> collection,
@Comment(name = "maps", value = "要插入的集合") List<Map<String, Object>> maps) {
collection.insertMany(maps.stream().map(Document::new).collect(Collectors.toList()));
}
@Comment("执行单条插入操作")
public void insert(MongoCollection<Document> collection,
@Comment(name = "map", value = "执行插入数据") Map<String, Object> map) {
insert(collection, Collections.singletonList(map));
}
@Comment("执行查询操作")
public FindIterable<Document> find(MongoCollection<Document> collection,
@Comment(name = "query", value = "查询条件") Map<String, Object> query) {
return collection.find(new Document(query));
}
@Comment("修改操作,返回修改数量")
public long update(MongoCollection<Document> collection,
@Comment(name = "query", value = "查询条件") Map<String, Object> query,
@Comment(name = "update", value = "修改值") Map<String, Object> update) {
return collection.updateOne(new Document(query), new Document(update)).getModifiedCount();
}
@Comment("批量修改,返回修改数量")
public long updateMany(MongoCollection<Document> collection,
@Comment(name = "query", value = "修改条件") Map<String, Object> query,
@Comment(name = "update", value = "修改值") Map<String, Object> update) {
return collection.updateMany(new Document(query), new Document(update)).getModifiedCount();
}
@Comment("批量修改,返回修改数量")
public long updateMany(MongoCollection<Document> collection,
@Comment(name = "query", value = "查询条件") Map<String, Object> query,
@Comment(name = "update", value = "修改值") Map<String, Object> update,
@Comment(name = "filters", value = "过滤条件") Map<String, Object> filters) {
UpdateOptions updateOptions = new UpdateOptions();
if (filters != null && !filters.isEmpty()) {
Object upsert = filters.get("upsert");
if (upsert != null) {
filters.remove("upsert");
updateOptions.upsert(Boolean.parseBoolean(upsert.toString()));
}
Object bypassDocumentValidation = filters.get("bypassDocumentValidation");
if (bypassDocumentValidation != null) {
filters.remove("bypassDocumentValidation");
updateOptions.bypassDocumentValidation(Boolean.parseBoolean(bypassDocumentValidation.toString()));
}
List<Document> arrayFilters = filters.entrySet().stream().map(entry -> new Document(entry.getKey(), entry.getValue())).collect(Collectors.toList());
updateOptions.arrayFilters(arrayFilters);
}
return collection.updateMany(new Document(query), new Document(update), updateOptions).getModifiedCount();
}
@Comment("查询数量")
public long count(MongoCollection<Document> collection,
@Comment(name = "query", value = "查询") Map<String, Object> query) {
return collection.countDocuments(new Document(query));
}
@Comment("批量删除,返回删除条数")
public long remove(MongoCollection<Document> collection,
@Comment(name = "query", value = "删除条件") Map<String, Object> query) {
return collection.deleteMany(new Document(query)).getDeletedCount();
}
@Comment("删除一条,返回删除条数")
public long removeOne(MongoCollection<Document> collection,
@Comment(name = "query", value = "删除条件") Map<String, Object> query) {
return collection.deleteOne(new Document(query)).getDeletedCount();
}
}

View File

@@ -0,0 +1,29 @@
package org.ssssssss.magicapi.mongo;
import com.mongodb.client.FindIterable;
import com.mongodb.client.MongoCursor;
import org.bson.Document;
import org.ssssssss.script.annotation.Comment;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
/**
* Mongo FindIterable 方法扩展
*
* @author mxd
*/
public class MongoFindIterableExtension {
@Comment("结果转为List")
public List<Map<String, Object>> list(FindIterable<Document> iterable) {
MongoCursor<Document> cursor = iterable.iterator();
List<Map<String, Object>> result = new ArrayList<>();
while (cursor.hasNext()) {
result.add(cursor.next());
}
return result;
}
}

View File

@@ -0,0 +1,97 @@
package org.ssssssss.magicapi.mongo;
import com.mongodb.client.MongoCollection;
import com.mongodb.client.MongoDatabase;
import org.apache.commons.lang3.StringUtils;
import org.bson.Document;
import org.bson.conversions.Bson;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.ssssssss.magicapi.core.config.Constants;
import org.ssssssss.magicapi.core.config.MagicModule;
import org.ssssssss.script.convert.ClassImplicitConvert;
import org.ssssssss.script.reflection.JavaInvoker;
import org.ssssssss.script.reflection.JavaReflection;
import org.ssssssss.script.runtime.Variables;
import java.lang.reflect.Method;
import java.util.HashMap;
import java.util.Map;
/**
* mongo模块
*
* @author mxd
*/
public class MongoModule extends HashMap<String, MongoModule.MongoDataBaseGetter> implements MagicModule, ClassImplicitConvert {
private static final Logger logger = LoggerFactory.getLogger(MongoModule.class);
private JavaInvoker<Method> invoker;
private Object factory;
public MongoModule(MongoTemplate mongoTemplate) {
JavaInvoker<Method> mongoDbFactoryInvoker = JavaReflection.getMethod(mongoTemplate, "getMongoDbFactory");
if(mongoDbFactoryInvoker == null){
mongoDbFactoryInvoker = JavaReflection.getMethod(mongoTemplate, "getMongoDatabaseFactory");
}
if (mongoDbFactoryInvoker != null) {
try {
factory = mongoDbFactoryInvoker.invoke0(mongoTemplate, null, Constants.EMPTY_OBJECT_ARRAY);
invoker = JavaReflection.getMethod(factory, "getDb", StringUtils.EMPTY);
if (invoker == null) {
invoker = JavaReflection.getMethod(factory, "getMongoDatabase", StringUtils.EMPTY);
}
} catch (Throwable e) {
logger.error("mongo模块初始化失败", e);
}
} else {
logger.error("mongo模块初始化失败");
}
JavaReflection.registerImplicitConvert(this);
}
@Override
public MongoDataBaseGetter get(Object databaseName) {
try {
if (databaseName == null) {
return null;
}
MongoDatabase database = (MongoDatabase) invoker.invoke0(factory, null, new Object[]{databaseName.toString()});
return new MongoDataBaseGetter(database);
} catch (Throwable e) {
throw new RuntimeException(e);
}
}
@Override
public String getModuleName() {
return "mongo";
}
@Override
public boolean support(Class<?> from, Class<?> to) {
return Map.class.isAssignableFrom(from) && (Bson.class.isAssignableFrom(to));
}
@Override
public Object convert(Variables variables, Object source, Class<?> target) {
return new Document((Map<String, Object>) source);
}
public static class MongoDataBaseGetter extends HashMap<String, MongoCollection<Document>> {
MongoDatabase database;
public MongoDataBaseGetter(MongoDatabase database) {
this.database = database;
}
@Override
public MongoCollection<Document> get(Object key) {
return database.getCollection(key.toString());
}
}
}

View File

@@ -0,0 +1 @@
org.springframework.boot.autoconfigure.EnableAutoConfiguration=org.ssssssss.magicapi.mongo.MagicMongoConfiguration