Flink Java Table API & SQL 之实时订单统计

Order 实体类

package com.daidai.source.mocksource.domain;

import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;

@Data
@AllArgsConstructor
@NoArgsConstructor
public class Order {
    private String id;
    private Integer userId;
    private Integer money;
    private Long createTime;
}

需求


就是每隔5秒统计最近5秒的每个用户的订单总数、订单的最大金额、订单的最小金额

主程序

package com.daidai.table;

import com.daidai.source.mocksource.domain.Order;
import org.apache.flink.api.common.eventtime.WatermarkStrategy;
import org.apache.flink.api.java.tuple.Tuple2;
import org.apache.flink.streaming.api.datastream.DataStream;
import org.apache.flink.streaming.api.datastream.DataStreamSource;
import org.apache.flink.streaming.api.datastream.SingleOutputStreamOperator;
import org.apache.flink.streaming.api.environment.StreamExecutionEnvironment;
import org.apache.flink.streaming.api.functions.source.SourceFunction;
import org.apache.flink.table.api.Table;
import org.apache.flink.table.api.bridge.java.StreamTableEnvironment;
import org.apache.flink.types.Row;

import java.time.Duration;
import java.util.Random;
import java.util.UUID;
import java.util.concurrent.TimeUnit;

import static org.apache.flink.table.api.Expressions.$;

public class RealtimeOrderStatistics {
    public static void main(String[] args) throws Exception {
        StreamExecutionEnvironment env = StreamExecutionEnvironment.getExecutionEnvironment();
        StreamTableEnvironment tableEnv = StreamTableEnvironment.create(env);

        DataStreamSource<Order> source = env.addSource(new SourceFunction<Order>() {
            private Boolean isRunning = true;

            @Override
            public void run(SourceContext<Order> ctx) throws Exception {
                while (isRunning) {
                    Random random = new Random();
                    Order order = new Order(
                            UUID.randomUUID().toString(),
                            random.nextInt(3),
                            random.nextInt(100),
                            System.currentTimeMillis()
                    );
                    TimeUnit.SECONDS.sleep(1);
                    ctx.collect(order);
                }
            }

            @Override
            public void cancel() {
                isRunning = false;
            }
        });

        SingleOutputStreamOperator<Order> watermarks = source
                .assignTimestampsAndWatermarks(WatermarkStrategy.<Order>forBoundedOutOfOrderness(Duration.ofSeconds(2))
                        .withTimestampAssigner((event, timestamp) -> event.getCreateTime()));

        tableEnv.createTemporaryView("t_order", watermarks, $("id"), $("userId"), $("money"), $("createTime").rowtime());

        String sql = "select " +
                "userId," +
                "count(money) as totalCount," +
                "max(money) as maxMoney," +
                "min(money) as minMoney " +
                "from t_order " +
                "group by userId," +
                "tumble(createTime, interval '5' second)";

        Table result = tableEnv.sqlQuery(sql);

        DataStream<Tuple2<Boolean, Row>> orderResult = tableEnv.toRetractStream(result, Row.class);

        orderResult.print();

        env.execute();
    }
}

注意事项

这种空格得千万注意,不然就得和我一样找大半天错误 ,如果你是用 Table 风格的话,应该不会有这种担忧。
Flink Java Table API & SQL 之实时订单统计_第1张图片

你可能感兴趣的:(Flink,java,flink,sql)