ServiceFramework作为Java Web框架都有哪些不错的设计

前言

最近需要开发一个纯API的项目,mlsql-cluster,从无到有,到最后完整的proxy功能开发完毕,只花了四个小时不到,自己不尽小感叹了一把 ServiceFramework的高效。

关于ServiceFramework的诞生

ServiceFramework算是一个古老的,基于Java的web框架了。我印象中应该是我11年的作品,那个时候应该是RubyOnRails正火的时候。我做了一段时间Rails程序员,后面转型做搜索,期间觉得没啥好用的Web框架,于是就开发了ServiceFramework。

极致简约的要求

早年Java语言的笨拙一直是广受诟病的,业务还没两行,代码和配置就已经几百上千行了。首先我们不可能改变这门语言,那么如何做到极致简约呢?自动生成源码的套路肯定不行,用户就天天通过各种命令生成源码去了,而且通常生成的源码又丑又难看,还不敢改,所以我们需要无声无息的为用户生成必要的代码, 并且还不能让用户看见,还需要兼顾IDE的代码提示。那么,应该怎么玩呢? 核心在于两个点,我们后续会展开讲:

运行时代码生成(codegen,功能增强)+ 父类方法签名(代码提示)

极致简约体现在哪

应用包含容器

早年几乎清一色的,代码都是跑在容器里的(weblogic,tomcat等)。在11年的时候,SF做出了一个重要的设计,就是http只是代码对外暴露的一个交互方式,和RPC一样,Web容器只是你运行代码里的一个组件而已。所以SF的启动是这样的(演示代码都是用Scala写的哈):

就是一个普通的Main方法。大家有没有发现现在大部分Web框架已经都这么干了。

配置文件精简

早年Java领域出现了一个潮流,就是能配置的坚决不写代码,配置可以更灵活,但是它们忘了配置本身也是一种代码(语法受限的语言),反倒增加了成本,所以后面引入了Annotation以及约定俗成。SF设计之初,就只有两个配置文件,一个application.yml,一个logging.yml文件。基本需要配置的很少。核心就是一个数据库配置信息,然后一个http端口。

自动读取数据库配置ORM

个人感觉对数据库的操作很难比SF更简化了(吹牛)。在SF中ORM是无任何配置文件的,唯一的信息就是在application.yml里的链接信息:

接着你按传统的方式在数据库里建好表,比如

1 CREATE TABLE backend
2 (
3   id                   int(11) NOT NULL AUTO_INCREMENT,
4   name                 varchar(255) DEFAULT NULL,
5   url                  text,
6   tag                  text,
7   ecs_resource_pool_id int(11),
8   PRIMARY KEY (id)
9 ) ENGINE=InnoDB DEFAULT CHARSET=utf8;

创建了一张backend表。然后我要在代码中怎么操作呢?一行代码就是一个Model。

1 public class Backend extends Model {
2 }

什么都没有啊? 就这么个类,我们看看怎么操作数据库,首先是新建一条记录:

1 Map<String, Object> newParams = new HashMap<>();
2 newParams.put(......)
3 Backend backend = Backend.create(newParams);
4 backend.save();

找到并且删除一条记录:

Backend backend = Backend.where(map("name","jack")).fetchOne()
backend.delete()

那没有申明属性,怎么访问属性呢?

String name = backend.attr("name",String.class)

当然,因为我经常会用name属性,我们就申明一下,方便代码提示,不申明可以通过attr去定向拿:

public class Backend extends Model {
        private String name;
        public String getName() {
              return name;
         }
}

记住,这里的代码纯粹是为了做代码提示,不是必须的。

你可能会问,ORM里的关联咋办?

public class Backend extends Model {
       @OneToMany
       private List< Info>  infos;
       public Association infos(){
           throw new AutoGeneration();
        }
}

这就是所有,接着你就可以通过类似backend.infos.where(....).fetch()来操作。你不用写任何逻辑代码,ORM会根据你的数据库读取到的元数据自动帮你做关联,自动填充属性,自动提供查询语法(代码提示通过Model类已经写好的方法完成)

Web Contorller,一切只为便捷。

写一个controller 以及一个action,你只要这么做:

1 class BackendController extends ApplicationController {
2    @At(path = Array("/backend/add"), types = Array(GET, POST))
3   def backendAdd = {
4     List("url", "tag", "name").foreach(item => require(hasParam(item), s"${item} is required"))
5     Backend.newOne(params(), true)
6     BackendService.refreshCache
7     render(map("msg", "success"))
8   }
9 }

继承ApplicationController,就是一个controller,@就定义了请求的endpoint。http参数怎么获取?使用param方法:

val name = param("name")
paramAsInt("times",0) // 获取int类型参数,并且默认值设置为0
hasParam("name")//判断有没有
params() //拿到所有参数

比如前面的例子,我们鼓励直接在controller里使用模型类操作数据库,免去了service的麻烦,因为model已经具有足够的表达能力,很多业务逻辑也可以放在model里。

这不比通过定义方法的参数强很多?定义方法的参数你会说便于测试,我们看SF怎么做接口测试的:

1 @Test
2   public void search() throws Exception {
3       RestResponse response = get("/doc/blog/search", map(
4               "tagNames", "_10,_9"
5       ));
6       Assert.assertTrue(response.status() == 200);
7       Page page = (Page) response.originContent();
8       Assert.assertTrue(page.getResult().size() > 0);
9   }

So Easy.

基于HTTP协议的伪RPC协议

越来越多的人喜欢HTTP协议而非PPC, PRC无论测试还是复杂度其实都大于HTTP,但是每次调用HTTP接口还是很麻烦的,SF提供了一个对HTTP自动包装的接口(动态生成代理类的方式),你只要提供HTTP接口代码,就可以直接使用。比如:

 1 trait BackendService {
 2   @At(path = Array("/run/script"), types = Array(GET, POST))
 3   def runScript(@Param("sql") sql: String): HttpTransportService.SResponse
 4
 5   @At(path = Array("/run/script"), types = Array(GET, POST))
 6   def runScript(params: Map[String, String]): HttpTransportService.SResponse
 7
 8   @At(path = Array("/run/sql"), types = Array(GET, POST))
 9   def runSQL(params: Map[String, String]): HttpTransportService.SResponse
10
11   @At(path = Array("/instance/resource"), types = Array(GET, POST))
12   def instanceResource(params: Map[String, String]): HttpTransportService.SResponse
13 }

这个接口是没有任何实现的,他对应的是后端一个服务的http接口。接着我们在SF里就可以这么调用了:

val instance = ClientProxy.get[BackendService]()
instance.runScript(params().asScala.toMap)

是不是很easy,很PRC?

后话

使用SF,你只需要几分钟就能搭建一个可以运行,具备部分业务逻辑功能的API服务。去掉尽量多的层,尽量让使用者可以用最简单的办法去完成对应的功能而不是去考虑一些设计的优雅性来完成一些功能特点。 大家可以查看mlsql-cluster 获得更多使用范例,感受其魅力。

另外,我个人认为比较完美的一个组合是: Reactjs + ServiceFramework ?? . React是一个我很让我有愿意去写代码的的前端框架。

原文地址:https://www.cnblogs.com/aishangJava/p/10105533.html

时间: 2024-10-10 15:14:52

ServiceFramework作为Java Web框架都有哪些不错的设计的相关文章

Java Web框架-----------------------struts2(官网教程版HelloWorld)

Java Web框架------------------struts2(官网教程版HelloWorld) 我们都知道Struts是Java Web 常用的三大框架之一,另外还有Spring.Hibernate.学习Struts很有必 要!那么怎么学习呢?我的建议是: 1.对于英语能力还可以的人,学技术我们要从官网文档学起,再结合中文别人所写的论文.博客,视频 等.这样可以达到事半功倍的效果. 2.对于阅读英语稍微吃力的人,我们可以下载有道词典,再来本计算机专业英语书,不懂就查,但是, 我们决不能

JAVA web 框架集合

“框架”犹如滔滔江水连绵不绝, 知道有它就好,先掌握自己工作和主流的框架: 在研究好用和新框架. 主流框架教程分享在Java帮帮-免费资源网 其他教程需要时间制作,会陆续分享!!! 152款框架,你还知道其他的吗? 留言你用过的web框架 Java开源web框架汇总 1 Struts2 Struts2是一个web应用框架.它不是一个Struts的新的发布版本,而是一个全新的框架.Struts2 是第二代基于Model-View-Controller (MVC)模型的web应用框架. Struts

java web 框架之struts2

简介:struts2是一个典型的mvc架构.利用它可是方便的实现某些功能. struts2 的工作流程图以及动态的action: 浏览器请求经过web容器,进入到struts2过滤器,然后搜索匹配,如果有与之对应的action对象,就会调用action对象的execut()方法,并根据处理的结果返回相应的值.通过创建多个action对象可以实现动态的action.也就是为了解决业务请求的多样性. 园长第一次接触框架,对于struts2框架的配置并不是很熟悉,对于初学者来说,很有必要讲讲strut

【EatBook】-NO.3.EatBook.3.JavaArchitecture.2.001-《架构探险:从零开始写Java Web框架》-

1.0.0 Summary Tittle:[EatBook]-NO.3.EatBook.3.JavaArchitecture.2.001-<架构探险:从零开始写Java Web框架>- Style:JavaArchitecture Series:Architecture Publishing House:电子工业 Author: 黄勇 Page Number:349 Since:2017-04-06 End:ing... Total Hours:ing... Degree Of Diffcul

Java Web入门项目之“网络交友”的设计与实现

前言:这个小项目是我刚学习JSP时,参考"JSP程序设计"这本书写的.这里之所以说参考这本书而不是照着这本书写,主要是因为我自己完成的时候删掉了不少繁琐的写法(比如:文件上传):同时对书中容易产生SQL注入漏洞,XSS跨站脚本漏洞等地方的写法进行了修改过滤:登录页面加上了随机验证码.除此之外,还添加了文件管理功能 PS:整个项目没有特别的难点,可以分为一个个功能点实现,大神轻喷,个人认为对初学Java Web的童鞋还是有参考意义的 注:整个项目的完整源代码和sql文件我会在文末给出下载

Java Web框架:Struts2简介

历史 Struts历史.JSP经历了JSPModel1和JSPModel2阶段.JSPModel1就像现在的PHP一样,每个文件中都混合了业务逻辑和HTML代码,每个JSP都直接与数据库交互.这种模型非常具有局限性,代码重用性较差.后面出现了改进版本的JSPModel1,它增加了JavaBean.JSP文件需要通过JavaBean间接访问数据库.JSPModel2中使用了三种技术:Servlet.JavaBean.JSP.Servlet相当于控制器,负责流程的控制,将请求进行分派,调用JavaB

从零写Java Web框架——实现Ioc依赖注入

大概思路 通过读取配置文件,获取框架要加载的包路径:base-package,类似于 Spring 配置文件中的: <context:component-scan base-package="*"/> 将 base-package 路径下的所有类都加载,并保存在一个 Set<Class<?>> classSet 中: 初始化 Bean 容器,遍历 classSet,通过反射获得 Class 的实例,并保存 Class 与 Class实例的映射关系,即

Java Web框架——自己动手实现一个简化版的Spring IOC框架

一.序 只要是Java Web的开发者,相信没有不知道大名鼎鼎的Spring框架的.作为一个优秀的开源框架,Spring包含9大组件,如果想要通过源码去理解每一个组件,复杂度和所花费的时间都容易让人望而却步--笔者平时习惯阅读源码,但是在学习Spring这种级别的框架面前显然不是一个好选择.但是问题又来了,不阅读源码,如何深入理解Spring呢?笔者在搜索学习资料的时候在github找到了一个优秀的repo--https://github.com/code4craft/tiny-spring,通

no java web 框架选型 + web 前端框架选型 实践

以前,觉得web框架的唯一选择是 java spring 全家桶,但用起来踊实比较重,配置文件比较重,开发起来比较重,在专注于写业务核心代码时,已经要做不少框架配置的事; 后来用了下python ,比java自由,但又不想js那么太目由,而且也支持类,把python当成java用很好用; 又去查了一下python能开发什么,web也是支持的,试了flask ,开发很简单,可以很快专注于业务逻辑; python性能比不上java ,又查到了tornado ,性能要好些,而且是面向对象的封装,用着比