使用javalin框架开发简单的web应用

405 阅读3分钟

最近了解到一款轻量级的web 开发框架,刚好最近需要开发一些简单,但是时间比较紧的web应用,就萌生出使用该框架的想法。

1.开发环境

JDK版本:17

Javalin版本:6.1.3

参考资料Javalin

2.使用方式

在pom 文件内导入依赖

<dependency>  
    <groupId>io.javalin</groupId>  
    <artifactId>javalin</artifactId>  
    <version>6.1.3</version>  
</dependency>

如果需要使用到日志输出,需要导入以下依赖

<dependency>  
    <groupId>org.slf4j</groupId>  
    <artifactId>slf4j-simple</artifactId>  
    <version>2.0.10</version>  
</dependency>

如果需要接口返回json格式,需要导入以下依赖

<dependency>  
    <groupId>com.fasterxml.jackson.core</groupId>  
    <artifactId>jackson-databind</artifactId>  
    <version>2.16.1</version>  
</dependency>

2.1.启动web 服务

通过以下一行的代码,即可以启动一个端口为7070的web服务

var app = Javalin.create().start(7070);

2.2.定义Api接口

启动服务后,可以获取到Javalin对象 app,可以通过app设置对应的接口

//定义一个get 请求
app.get("/test", ctx -> {  
    Map<String, String> map = new HashMap<>();  
    map.put("resultCode", "1");  
    map.put("resultMsg", "get : hello world");  
    ctx.json(map);  
});

//定义一个post 请求
app.post("/test", ctx -> {  
    Map<String, String> map = new HashMap<>();  
    map.put("resultCode", "1");  
    map.put("resultMsg", "post : hello world");  
    ctx.json(map);  
});

//定义一个put 请求  
app.put("/test", ctx -> {  
    Map<String, String> map = new HashMap<>();  
    map.put("resultCode", "1");  
    map.put("resultMsg", "put : hello world");  
    ctx.json(map);  
});

//定义一个delete 请求  
app.delete("/test", ctx -> {  
    Map<String, String> map = new HashMap<>();  
    map.put("resultCode", "1");  
    map.put("resultMsg", "delete : hello world");  
    ctx.json(map);  
});

2.3.获取接口的请求参数

你可以通过ctx对象获取到请求的参数,该ctx在 get/post/put/delete中使用方法一样

获取地址栏上的?传参

app.get("/hello", ctx -> {  
  
    //获取在地址栏上通过?传递的某个参数?name=aaa  
    String name = ctx.queryParam("name");  
  
    //获取在地址栏上通过?传递的所有参数?name=aaa&age=18  
    Map<String, List<String>> queryParamMap = ctx.queryParamMap();  
  
    Map<String, String> map = new HashMap<>();  
    map.put("resultCode", "1");  
    map.put("resultMsg", "get : hello world");  
    ctx.json(map);  
});

获取路径参数

app.get("/hello/{name}", ctx -> {  
  
    //获取在路径传递的某个参数/hello/{name}  
    String name = ctx.pathParam("name");  
    //获取在路径传递的所有参数/hello/{name}  
    Map<String, String> pathParamMap = ctx.pathParamMap();  
     
  
    Map<String, String> map = new HashMap<>();  
    map.put("resultCode", "1");  
    map.put("resultMsg", "get : hello world");  
    ctx.json(map);  
});

获取在request body内传递参数

app.post("/hello", ctx -> {  
  
    User user = ctx.bodyAsClass(User.class);  
  
    ctx.json(user);  
});

 

//定义一个测试用的User对象

class User {  
    private String name;  
    private int age;  
  
    public String getName() {  
        return name;  
    }  
  
    public void setName(String name) {  
        this.name = name;  
    }  
  
    public int getAge() {  
        return age;  
    }  
  
    public void setAge(int age) {  
        this.age = age;  
    }  
  
    @Override  
    public String toString() {  
        return "User{" +  
                "name='" + name + '\'' +  
                ", age=" + age +  
                '}';  
    }  
}

2.4.Api请求拦截

//调用请求之前,无论该路径是否存在(包括404),都会进入拦截
app.before("/test/*", ctx -> ctx.result("before "+ctx.url()));

//调用请求之后,无论该路径是否存在(包括404),都会进入拦截
app.after("/test/*", ctx -> ctx.result("after  "+ctx.url()));

//调用请求之前,该路径存在(没有触发404),会进入拦截
app.beforeMatched("/test/*", ctx -> ctx.result("beforeMatched "+ctx.url()));

//调用请求之后,该路径存在(没有触发404),会进入拦截
app.afterMatched("/test/*", ctx -> ctx.result("afterMatched "+ctx.url()));

可以通过ctx获取到请求的参数,详细可参考2.3

2.5.异常拦截

app.exception(Exception.class, (e, ctx) -> ctx.result("exception : " + e.getMessage()));

可以通过ctx获取到请求的参数,详细可参考2.3

2.6.路由分组

路由分组可以通过在创建Javalin对象的时候通过router.apiBuilder进行配置

var app = Javalin.create(config -> {
            config.staticFiles.add("template");
            config.router.apiBuilder(() -> {
                path("/test", () -> {
                    get("/hello", ctx -> ctx.result("Hello World"));
                    before("/*", ctx -> System.out.println("Before" + ctx.url()));
                });
            });
        })
        .start(7070);

通过path方法指定父级路由,在path 方法内的所有请求和拦截器都会以父级路由的路径作为开头

例如上面的例子,/hello定义在path /test下,则请求的路径为/test/hello

拦截器/*定义在path /test下,则拦截/test/下的所有请求