精华内容
下载资源
问答
  • Redis 队列 Java调用简单实现
    2021-02-12 14:44:35

    简述

    在本博客中,我们将会创建一个reids的消息队列,Redis可以被当成消息队列使用。消息会被存放在一个key-value集合中。

    redis消息生产者使用RPUSH命令将消息添加到队列的尾部,而消息消费者可以使用BLPOP命令获取列表开头的消息,使用FIFO(先进先出)规则。

    注意:本博客前置条件,熟悉redis并且知道如何启动redis服务器

    Redis 队列实现需要的maven依赖

    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">

    4.0.0

    com.leftso.redis

    message-queue

    1.0.0-SNAPSHOT

    REDDIS - ${project.artifactId}

    http://leftso.com

    redis.clients

    jedis

    2.7.2

    Redis消息队列生产者

    我们先使用rpush()方法将消息发布到mq-key队列中。这条消息将会添加到列表的最末端。

    import redis.clients.jedis.Jedis;

    public class MessageProducer {

    public static void main(String... args) {

    Jedis jedis = new Jedis("localhost");

    jedis.rpush("mq-key", "first message");

    jedis.rpush("mq-key", "second message");

    jedis.rpush("mq-key", "third message");

    }

    }

    Redis消息队列消费者

    我们可以使用lpop()或者blpop()方法来消费消息。下面我们将会使用阻塞的lpop 方法,就如方法名称一样,使用该方法线程会进入阻塞状态直到下一个消息过来。我们可以设置一个等待消息的超时时间。下面设置的超时时间为0,表示永久等待没有超时时间。

    import redis.clients.jedis.Jedis;

    import java.util.List;

    public class MessageConsumer {

    private static final int TIMEOUT = 0;

    public static void main(String... args ) {

    Jedis jedis = new Jedis("localhost");

    while(true){

    System.out.println("Waiting for a message in the queue");

    List messages = jedis.blpop(TIMEOUT, "mq-key");

    System.out.println("received message with key:" + messages.get(0) + " with value:" + messages.get(1));

    }

    }

    }

    启动消息队列消费者

    $title(console)

    Waiting for a message in the queue

    启动消息队列生产者

    $title(console)

    Waiting for a message in the queue

    received message with key:mq-key with value:first message

    Waiting for a message in the queue

    received message with key:mq-key with value:second message

    Waiting for a message in the queue

    received message with key:mq-key with value:third message

    Waiting for a message in the queue

    参考文档:

    更多相关内容
  • php队列+php-redis队列+php-redis扩展,php入队出队,redis入队出队以及其php .dll扩展
  • 1、linxu挂起队列监听 nohup php artisan queue:listen --timeout=90 --tries=1 >> /dev/null 2>&1 & 2、发现问题(日志) In Process.php line 429: The process has been sinaled with signal "1". 3、查询...
  • 里为大家带来Python的Flask框架应用调用Redis队列数据的方法,从而能够实现异步无阻塞从而提高某些实时处理情况下程序的性能,需要的朋友可以参考下
  • Thinkphp6 redis队列 消息事件 gatewayworker聊天打通版
  • 抽奖系统后台 springboot+mybatis redis队列处理高并发
  • redis队列弹幕

    2019-08-10 08:04:48
    redis队列弹幕
  • 小伙伴们大家好,不知道你们有没有在Java开发中遇到redis队列高并发,这个问题让你很头疼,今天小编就来讲解一下在Java中遇到redis队列高并发了,到底该怎么办。高并发的业务场景:我们做商品抢购功能,要面临的第一...

    小伙伴们大家好,不知道你们有没有在Java开发中遇到redis队列高并发,这个问题让你很头疼,今天小编就来讲解一下在Java中遇到redis队列高并发了,到底该怎么办。

    高并发的业务场景:

    我们做商品抢购功能,要面临的第一个问题就是数据不能异常,而保证数据不异常我们的解决办法有很多比如说数据库的锁机制,或者先改后查的方式都能解决,但是第二个问题来了如果我们用上述技术解决,数据是不会异常了,但是我们的服务器压力就会很大了,从而使服务器宕机,那么我们如何使服务器压力减小还能保证数据不异常呢,我们可以使用队列的思想,下面我们介绍的是使用redis队列解决高并发的问题

    设计思路

    用户在下订单之前当然是先查询到这个商品,在这个查询的时候,将数据库中商品的剩余数量存到redis中;

    服务器在一瞬间接到成千上万的下订单请求,在控制层没有直接处理请求数据,而是先根据redis中商品的剩余数量来判断,如果>0,就将请求放到请求队列中,否则直接响应客户端“卖完了”;

    考虑到数据的一致性,队列的容量就是商品的剩余数量,队列采用的是线程安全的队列LinkedBlockingQueue(单台服务器),然后通过新的线程异步处理这些请求,多台服务器的话,可以考虑使用消息队列MQ,单独用一台服务器去处理消息队列中的请求;

    客户端发送订单请求之后,会收到响应,要么是剩余数量不足(卖完了),要么是请求已经被放到队列中,为下一步的轮询订单做准备;

    如果响应状态是卖完了,直接提示客户,如果请求已经放入队列中,就可以根据用户id和商品id去轮询订单了;

    实现步骤

    说明:用java语言,springmvc框架+redis实现

    准备工作,查询商品信息,将剩余数量同步到redis中 Jedis jedis = jedisPool.getResource();

    BuyGood good=buyGoodService.getById(good_id);

    jedis.set("residue"+good_id, good.getResidue()+"");

    jedisPool.returnResource(jedis);

    下订单的方法,下面直接展示代码,包括请求对象,控制层方法,请求处理线程类的具体实现

    请求封装对象 public class BuyRequest {

    private int good_id;//商品id

    private int user_id;//用户ID

    private int order_id;//订单id

    private BuyOrders buyOrders;//订单信息

    private int response_status;//0:未处理;1:正常;2:异常

    public BuyOrders getBuyOrders() {

    return buyOrders;

    }

    public void setBuyOrders(BuyOrders buyOrders) {

    this.buyOrders = buyOrders;

    }

    public int getGood_id() {

    return good_id;

    }

    public void setGood_id(int good_id) {

    this.good_id = good_id;

    }

    public int getOrder_id() {

    return order_id;

    }

    public void setOrder_id(int order_id) {

    this.order_id = order_id;

    }

    public int getResponse_status() {

    return response_status;

    }

    public void setResponse_status(int response_status) {

    this.response_status = response_status;

    }

    public int getUser_id() {

    return user_id;

    }

    public void setUser_id(int user_id) {

    this.user_id = user_id;

    }

    }

    处理请求的controller @Controller

    @RequestMapping("/buy")

    public class BuyController {

    private static BuyQueuebuyqueue =null;//线程安全的请求队列

    @RequestMapping("/addOrders.do")

    @ResponseBody

    public Object addOrders(BuyRequest buyrequest){

    Mapresults = new HashMap<>();

    Jedis jedis = jedisPool.getResource();

    try {

    //下订单之前,先获取商品的剩余数量

    int residue =

    Integer.valueOf(jedis.get("residue"+buyrequest.getGood_id()));

    if(residue<1){//如果剩余数量不足,直接响应客户端“卖完了”

    results.put("msg", "卖完了");

    results.put("done", false);

    BaseLog.info("addOrders results="+JSON.toJSONString(results));

    return results;

    }

    //如果还有剩余商品,就准备将请求放到请求队列中

    if(buyqueue==null){//第一次初始化请求队列,队列的容量为当前的商品剩余数量

    buyqueue=new BuyQueue(residue);

    }

    if(buyqueue.remainingCapacity()>0){//当队列的可用容量大于0时,将请求放到请求队列中

    buyqueue.put(buyrequest);

    }else{//当请求队列已满,本次请求不能处理,直接响应客户端提示请求队列已满

    results.put("msg", "抢购队列已满,请稍候重试!");

    results.put("done", false);

    return results;

    }

    if(!DealQueueThread.excute){//如果线程类的当前执行标志为未执行,即空闲状态,通过线程池启动线程

    DealQueueThread dealQueue = new DealQueueThread(buyqueue);

    ThreadPoolUtil.pool.execute(dealQueue);

    BaseLog.info("Thread.activeCount()="+Thread.activeCount());

    }

    //请求放入到队列中,即完成下单请求

    results.put("done", true);

    results.put("msg", "下订单成功");

    } catch (Exception e) {

    results.put("done", false);

    results.put("msg", "下单失败");

    BaseLog.info("addOrders results="+JSON.toJSONString(results));

    BaseLog.error("addOrders",e);

    }finally{

    jedisPool.returnResource(jedis);

    }

    return results;

    }

    }

    处理请求的线程类 @Component

    public class DealQueueThread implements Runnable {

    private static DealQueueThread dealQueueThread;

    @Autowired

    BuyGoodService buyGoodService;

    @Autowired

    BuyOrdersService buyOrdersService;

    @Autowired

    JedisPool jedisPool;

    private Jedis jedis;

    private BuyQueuebuyqueue;

    public static boolean excute = false;//线程的默认执行标志为未执行,即空闲状态

    public DealQueueThread() {

    }

    public DealQueueThread(BuyQueuebuyqueue) {

    this.buyqueue = buyqueue;

    jedis = dealQueueThread.jedisPool.getResource();

    }

    @PostConstruct

    public void init() {

    dealQueueThread = this;

    dealQueueThread.buyGoodService = this.buyGoodService;

    dealQueueThread.buyOrdersService = this.buyOrdersService;

    dealQueueThread.jedisPool = this.jedisPool;

    }

    @Override

    public void run() {

    try {

    excute = true;//修改线程的默认执行标志为执行状态

    //开始处理请求队列中的请求,按照队列的FIFO的规则,先处理先放入到队列中的请求

    while (buyqueue != null && buyqueue.size() > 0) {

    BuyRequest buyreq = buyqueue.take();//取出队列中的请求

    dealWithQueue(buyreq);//处理请求

    }

    } catch (InterruptedException e) {

    BaseLog.error("DealQueueThread:", e);

    } finally {

    excute = false;

    }

    }

    public synchronized void dealWithQueue(BuyRequest buyreq) {

    try {

    //为了尽量确保数据的一致性,处理之前先从redis中获取当前抢购商品的剩余数量

    int residue = Integer.valueOf(jedis.get("residue" +

    buyreq.getGood_id()));

    if (residue < 1) {//如果没有剩余商品,就直接返回

    buyreq.setResponse_status(3);

    return;

    }

    //如果有剩余商品,先在redis中将剩余数量减一,再开始下订单

    jedis.decr("residue" + buyreq.getGood_id());

    //将数据库中将剩余数量减一,这一步处理可以在队列处理完成之后一次性更新剩余数量

    dealQueueThread.buyGoodService.minusResidue(buyreq.getGood_id());

    //处理请求,下订单

    BuyOrders bo = new BuyOrders();

    bo.setGood_id(buyreq.getGood_id());

    bo.setUser_id(buyreq.getUser_id());

    int order_id = dealQueueThread.buyOrdersService.insert(bo);

    BuyOrders orders = dealQueueThread.buyOrdersService.getById(order_id);

    buyreq.setOrder_id(order_id);//订单id

    buyreq.setBuyOrders(orders);//订单信息

    buyreq.setResponse_status(1);//处理完成状态

    } catch (Exception e) {

    buyreq.setResponse_status(2);//异常状态

    BaseLog.error("DealQueueThread dealWithQueue:", e);

    }

    }

    }

    轮询订单

    思路:查询订单和剩余数量,有以下三种情况:

    1)查到订单,直接跳转到确认订单并支付的页面完成支付;

    2)还没有查询到订单,但是剩余数量大于0,说明请求还在队列中,继续轮询;

    3)没有查到订单,剩余数量等于或小于0,说明抢购失败了,直接响应客户抢购失败;

    以上就是Java中使用redis队列解决高并发的一些内容,更多相关内容请持续关注本站。

    展开全文
  • Reids是一个比较高级的开源key-value存储系统,采用ANSI C实现。其与memcached类似,但是支持持久化数据存储
  • Redis队列和阻塞队列

    千次阅读 2021-10-08 15:46:10
    Redis队列 List 简单演示如下 普通的redis队列,为了实现业务,通常会使用while进行循环,这样的话没有消息时依旧会频繁的执行循环,造成cpu的空转,所以一般会在代码中增加sleep来解决该问题,但因此又会造成消息...

    redis 队列的优点是轻量级,业务足够简单时不需要使用rabbitMq这样专业的消息中间件;缺点是弹出队列中的元素时,即使该消息处理失败也无法再次进行消费

    Redis队列 List
    在这里插入图片描述

    简单演示如下
    在这里插入图片描述

    普通的redis队列,为了实现业务,通常会使用while进行循环,这样的话没有消息时依旧会频繁的执行循环,造成cpu的空转,所以一般会在代码中增加sleep来解决该问题,但因此又会造成消息延迟问题。
    在这里插入图片描述
    阻塞队列可以很好的解决这些问题。

    Redis阻塞队列

    redis队列提供了 “阻塞式” 拉取消息的命令:BRPOP / BLPOP,这里的 B 指的是阻塞(Block)。
    如果队列为空,消费者在拉取消息时就「阻塞等待」,一旦有新消息过来,就通知消费者立即处理新消息。
    在这里插入图片描述
    阻塞队列实现:
    在这里插入图片描述

    使用 BRPOP 这种阻塞式方式拉取消息时,还支持传入一个「超时时间」,如果设置为 0,则表示不设置超时,直到有新消息才返回,否则会在指定的超时时间后返回 NULL

    下面是某业务完整的消费者代码
    在这里插入图片描述
    注意:

    1. 阻塞时间结束后代码会继续向下执行
    2. 如果设置的超时时间太长,这个连接太久没有活跃过,可能会被 Redis Server 判定为无效连接,之后 Redis Server 会强制把这个客户端踢下线。所以,客户端要有处理机制。
      实际项目中redis连接超时时间远大于20s,因此正常情况不会出现redis超时问题。以防万一增加redis异常捕获,出现异常时杀掉当前进程,同时supervisord会自动重新拉起该进程
    展开全文
  • 本篇文章主要介绍了thinkphp+redis+队列的实现代码,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
  • mvc - redis队列dome

    2018-12-21 09:19:00
    来 源 互 联 网,希 望 你 对 你 们 有 帮 助。多 多 支 持。
  • 安装Redis和扩展配置 二.安装redis的依赖 三.配置laravel队列 四.创建队列 五.启动队列 六.使用队列 七.最终结果 一.安装Redis和扩展配置 这里就跳过,可以专门去看安装Redis以及配置PHP扩展的文章 二.安装...

    目录

    目录

    一.安装Redis和扩展配置

    二.安装redis的依赖

    三.配置laravel队列

    四.创建队列

    五.启动队列

    六.使用队列

    七.最终结果


    一.安装Redis和扩展配置

    这里就跳过,可以专门去看安装Redis以及配置PHP扩展的文章

    二.安装redis的依赖

    laravel根目录下运行命令 composer require predis/predis

    安装时报内存溢出

    PHP Fatal error:  Allowed memory size of 1610612736 bytes exhausted (tried to allocate 4096 bytes)

    解决:

    php -r "echo ini_get('memory_limit').PHP_EOL;"    //命令行执行,获取当前内存限制大小

    修改php.ini配置文件

    memory_limit = -1

    安装完后,再改回来

    三.配置laravel队列

    修改.env配置,将QUEUE_CONNECTION=sync改为

    QUEUE_CONNECTION=redis

    四.创建队列

    使用命令创建队列,在app/Jobs目录

    php artisan make:job TestQueue

    TestQueue.php文件

    <?php
    
    namespace App\Jobs;
    
    use Illuminate\Bus\Queueable;
    use Illuminate\Contracts\Queue\ShouldQueue;
    use Illuminate\Foundation\Bus\Dispatchable;
    use Illuminate\Queue\InteractsWithQueue;
    use Illuminate\Queue\SerializesModels;
    use Illuminate\Support\Facades\Cache;
    
    class TestQueue implements ShouldQueue
    {
        use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;
    
        public $data;
        /**
         * Create a new job instance.
         *
         * @return void
         */
        public function __construct($data)
        {
            //接收消息
            return $this->data = $data;
        }
    
        /**
         * Execute the job.
         *
         * @return void
         */
        public function handle()
        {
            //消费消息
            Cache::add('data', $this->data);
        }
    }
    

    五.启动队列

    起一个命令行,开启队列监听,频道为Test

    php artisan queue:listen redis --queue=Test

    六.使用队列

    往Test频道中投递消

    Route::get('job', function () {
        TestQueue::dispatch('队列消息')->onQueue('Test');
        return 'ok';
    });

    七.最终结果

    最终cache缓存文件中添加了数据

    9999999999s:12:"队列消息";
     
    展开全文
  • 本篇文章主要介绍了Java利用Redis实现消息队列的示例代码,小编觉得挺不错的,现在分享给大家,也给大家做个参考。一起跟随小编过来看看吧
  • php redis队列操作

    2021-05-07 12:50:14
    Binary Tree Inorder TraversalGiven a binary tree, return theinordertraversal of its nodes' values. For example:Given binary tre ...Bash漏洞批量检测工具与修复方案&amp;lt;img src=...
  • 1、异步队列处理 2、redis 过滤(就是只处理当天第一次请求) 3、redis 辅助存储app名称(验证过后批量插入数据app名称表中) 4、拼接插入的以及新增的如详细表中 解决办法: 1、接口修改 redis 过滤 + 如l
  • thinkphp redis队列配置

    千次阅读 2022-03-22 23:38:05
    若要禁用,则设置为 null 'default' => 'default', // 默认的队列名称 'host' => '127.0.0.1', // redis 主机ip 'port' => 6379, // redis 端口 'password' => '', // redis 密码 'select' => 1, // 使用哪一个 db...
  • java操作redis队列

    千次阅读 2018-12-26 15:48:38
    场景:  1....将json字符串写入队列  4.从队列中取出json字符串  5.将json字符串转换为对象本例主要jar包:  jedis-2.9.0.jar;fastjson-1.2.41.jar  本例三个类:  1. 实体类CityBean.java p...
  • 主要介绍了SpringBoot利用redis集成消息队列的方法,需要的朋友可以参考下
  • Redis队列操作方式list

    2021-03-04 10:18:29
    首先我们看下队列RedisDesktopManager 中保存的方式: 首先存储队列: (new Redis())->rPush('Tracking_num', $s); 以上从右侧存储数值 从左侧取出并删除一个 $redis = new Redis(); $track_num = $redis-&...
  • php中使用redis队列操作实例代码

    千次阅读 2019-05-17 10:05:43
    例1,入队操作: ...$redis = new Redis(); $redis->connect('127.0.0.1',6379); while(True){ try{ $value = 'value_'.date('Y-m-d H:i:s'); $redis->LPUSH('key1',$value); sleep(rand()%3);...
  • laravel使用redis队列

    2020-04-01 10:59:48
    1、队列配置文件是config/queue.php(这里我默认配置即可): 2、 创建迁移表(failed-table 、jobs、migrations) php artisan queue:table php artisan queue:failed-table php artisan migrate ps:出现下面...
  • Redis 队列和MQ 对比

    2021-12-08 14:23:10
    要过要使用其他类型的MQ中间件就需要购买资源,但程序运行中正常情况下不会用到这个备胎,因此剩下的选项就是将队列数据落到数据库(关系型/非关系型),要么就是redis,因为即便MQ出现问题,供应商也会很快的修复...
  • 主要介绍了基于python操作redis及消息队列,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
  • 下面小编就为大家带来一篇PHP实现电商订单自动确认收货redis队列。小编觉得挺不错的,现在就分享给大家,也给大家做个参考。一起跟随小编过来看看吧
  • 记一次队列的使用场景(Redis队列)

    千次阅读 2020-04-29 10:56:43
    前几天开发好了优惠券模块,在优惠券发放那里使用到了队列来进行异步处理,因公司规模较小,服务器配置只有2G,安装MQ占用了宝贵的内存资源,于是就使用了Redis自带的消息队列来实现。 技术栈: Redis+Quartz定时...
  • redis队列使用基于python的redis操作

    千次阅读 2018-09-27 15:13:05
    本文重点标题redis-python简单交互python直接连接redis,并进行简单设置操作python通过连接池连接redis,并进行简单设置操作redis队列操作redis-MQlpush, lrangerpoprpush,lpop小结 redis-python简单交互 关于...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 165,171
精华内容 66,068
关键字:

redis队列

友情链接: 63603868.rar