JS逆向之补环境过瑞数详解

JS逆向之补环境过瑞数详解

“瑞数” 是逆向路上的一座大山,是许多JS逆向者绕不开的一堵围墙,也是跳槽简历上的一个亮点,我们必须得在下次跳槽前攻克它!! 好在现在网上有很多讲解瑞数相关的文章,贴心的一步一步教我们去分析瑞数流程,分析如何去扣瑞数逻辑,企图以此教会我们 (手动狗头)。却鲜有文章详细去讲解如何通过纯补环境的方式过瑞数。今天,它来了!

为了让大家彻底搞定瑞数这个老大哥,本文将从以下四个部分进行描述:

  1. rs的流程逻辑
  2. 浅谈扣代码过rs
  3. 详解补环境过rs
  4. 扣代码与补环境对比
  5. 弯道超车环节

篇幅较长,坐稳发车咯!

*注:本文内容均以一个新人友好型 rs4网站: 网上房地产,为例;*

一:rs的流程逻辑

我们在做逆向的时候,首先得分析出哪些加密参数是需要逆向的,然后再是去逆向这些参数。当然瑞数也是一样。

所以我们第一步就是明确逆向的目标

  • 现象:上了rs的网站会请求两次page_url,第二次请求page_url时才能得到正确的页面内容;
  • 分析:分析其请求体,发现第二次请求page_url时带上了cookie_s和cookie_t, 而cookies_s是来自第一次请求page_url时其响应头set的;
  • 结论:那么我们的目标就确定了 -- 破解cookie_t的生成逻辑;

现在,我们知道了需要逆向的加密参数是cookie_t,那么cookie_t是从何而来呢,我们先分析一下网站的请求

瑞数网站请求流程分析:

第一次请求: 请求page_url,响应状态码202,响应头中 set了 cookie_s;

响应体是HTML源码,从上到下可以分为四部分:我先剧透一下它们的作用

  1. 一个meta标签,其content内容很长且是动态的(每次请求会变化),会在eval执行第二层JS代码时使用到;
  2. 一个外链js文件,一般同一页面中其内容是固定的,下面的自执行函数会解密文件内容生成eval执行时需要的JS源码,也就是第二层vm代码;
  3. 一个大自执行函数(每次请求首页都会动态变化),主要是解密外链JS内容,给window添加一些属性如$_ts,会在vm中使用;
  4. 末尾的两个script标签中的函数调用,会更新cookie,使其变长。这里我们可以不用关注这个。
    [外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5Y95CH4R-1673156546278)(https://note.youdao.com/yws/res/26818/WEBRESOURCE8752b7a5f31959082ecd992b3c0c4ace)]

第二次请求: 请求外链js,一般内容是固定的;

第三次请求: 请求page_url,返回200,携带cookie_s,cookie_T即可正常请求;

那么当我们在浏览器中访问该网站时到底发生了什么?其中有什么值得我们关注的?

我们先人工模拟一下浏览器加载page_url源码会发生什么:

  1. 浏览器加载meta ;
  2. 浏览器请求外链js并执行js内容;
  3. 执行page_url源码自执行函数,它内部会将外链js解密成eval需要的万行js字符串,并给window.$_ts添加了很多属性,然后调用eval函数进入VM执行解密后的js,生成cookie,eval执行完毕,继续执行自执行函数;
  4. 执行末尾script标签中的代码,这些代码会更新cookie_t(可以不用管
  5. 执行setTimeout、eventlistener回调函数(可以不用管

瑞数执行流程图解如下:

这里我们需要关注eval调用的位置(也就是VM的入口),cookie生成的位置

注:浏览器v8调用eval执行代码时会开启一个虚拟机(VM+数字)去执行JS代码。

我们直接hook eval搜索.call就可以定位到调用eval的位置

_$Ln就是解密后的js代码字符串;进入vm是一个自执行函数,其中有生成cookie的逻辑,定位cookie可以直接hook或在vm代码中搜索 (5)

hook cookie代码:

// hook  指定cookie赋值
(function () {
    'use strict';
    Object.defineProperty(document, 'cookie', {
        set: function (cookie) {
            if(cookie.indexOf("FSSBBIl1UgzbN7N80T")!= -1){
                debugger;
            }
            return cookie;
        }
    });
})();

好了,以上就是瑞数的整体流程逻辑,那么我们该如何通过扣代码去生成cookie_t过瑞数呢?

二、浅谈扣代码过瑞数

由于每次请求瑞数page_url,其源码是动态变化的,VM代码也是动态变化的,所以我们要保存一份静态代码方便调试;

直接如图这样,固定page_url响应即可,

这样请求时,page_url中的 外链JS是固定的,自执行函数是固定的,VM中的代码也是固定的,那么这份固定代码每次生成的cookie_t 是不是也固定呢?

答案:不是,因为cookie_t的生成用到了随机数时间戳,我们将这两个变量也hook固定住,最终生成的cookie_t就是固定的啦。

此时我们就可以开始扣这份静态代码了,扣到node生成的cookie_t与浏览器执行静态代码生成的cookie_t 一致就说明扣成功了。

扣代码需要扣两部分,page_url源码部分和VM中生成cookie_t部分。

按照我们之前的分析,VM中代码会用到window.$_ts,因此我们得先保证从page_url源码中扣下来的代码执行到eval时,能正常生成window.$_ts

我们将page_url的自执行函数外链JS内容先扣下来,meta content也先扣下来,然后根据执行报错简单补一下环境,使得扣下来代码执行到eval时,其window.$_ts和解密出的VM JS代码与本地静态代码生成的一致。

这就说明我们page_url源码部分扣好了,接下来就可以去扣VM中生成cookie_t的部分。

上面我们分析到cookie的定位,可以知道 _$bO这个函数中生成了二次cookie_t,那这就是我们扣代码的起点,将该函数扣到文件末尾,直接执行,然后缺啥补啥,遇到使用BOM、DOM api的代码时,我们可以使用等价逻辑替换,比如此处原逻辑是获取meta标签中的content内容,然后再删除meta标签,我们可以直接等价替换成 return meta_content。如图:

如果扣到最后,node生成的cookie_t与本地静态代码生成的不一致,则说明我们扣的代码有些环境检测没过,我们可以根据node与浏览器执行的差异去定位,比如node执行到某个地方的值与浏览器执行静态代码得到的不一样,说明前面逻辑有差异,继续向前定位,如此反复即可找出所有遗漏的环境检测,完成VM部分扣取。

此时我们就完成了这份静态rs代码的扣取并取得成功,但是rs网站的代码是动态的啊,每次请求时 window.$_tsVM js都会变化,难道我们每份都要去扣吗?不,其实我们现在离真正成功只差一个映射,

VM的万行js代码 虽然每次都会变化,但是变化的只是变量名,其他的都不变。

映射就是将动态window.$_ts中的属性名与 我们扣的VM 中JS用到的window.$_ts中的固定属性名一一对应。

所以在扣的过程中我们需要注意VM中哪些地方使用了外部变量,(即一个函数中,哪个变量来自其他作用域,就算外部变量),我们需要关注这些外部变量是从哪来的,如果是VM自执行函数中定义的,那就不用管,如果是来自window.$_ts,则需要记录下来,这就是需要映射传入的。

这里的计算逻辑使用到了 window.$_ts._$IK,所以我们要做映射时要传入这个值;window.$_ts={_$IK:对应的动态属性名}

解决完映射,也就成功扣代码过rs了。

好了,扣代码到此为止,接下来就是我们本文的重点。

三、详解补环境过rs

不知道补环境原理的同志可以参考我上篇文章:JS逆向之浏览器补环境详解;

其实纯补环境过瑞数原理很简单,我们来观察瑞数执行流程图解,基于浏览器环境执行这些动态JS可以生成可用的 cookie_t。那么只要我们补的浏览器环境足够完美,使得在这些动态JS看来,我们补的环境===浏览器环境,那么我们补的环境执行这些动态JS,同样也能生成可用的 cookie_t,然后我们再通过 document.cookie 将cookie_t 提取出来不就好了。

用伪代码表示就是:

// 补的环境头
window = this;
... 省略大量环境头
// 模拟meta标签及其content
document.createElement('meta');
Meta$content = "{qYnKTJPAw84QfF5jm0I2_1IqhgTvRw8Y0yCBPxIVn6od8AeJE6CBz8ZSU6U...省略";
// 固定的外链js
$_ts=window['$_ts'];if(!$_ts)$_ts={};$_ts.scj=[];$_ts['dfe1675']='þþ+...省略';
// page_url动态自执行函数
(function(){var _$CK=0,_$WI=[[9,3,6,0,4,1; ...ret = _$su.call(_$fr, _$WR); 很长...省略}}}}}}}})();;


// 获取cookie
function get_cookie(){
    return document.cookie;
}
// 获取MmEwMD参数
function get_mme(){{
    XMLHttpRequest.prototype.open("GET","http://脱敏/",true);
    return XMLHttpRequest.prototype.uri;
}}

这就是我们最后要补成的文件样子,由于Meta$content 和page_url动态自执行函数是动态变化的,因此我们每次请求page_url 都需要用正则提取出这两个字符串,然后拼接到该文件中,然后python pyexecjs调用get_cookie即可得到可用cookie_t;

在上面的扣代码过瑞数中也提到了,由于有随机数时间戳参与生成cookie_t 运算,导致同一份静态JS代码生成的cookie_t 是变化的,我们可以通过hook使得时间戳和随机数固定,这样同一份静态JS生成的cookie_t就是固定的。

// 固定定随机数和时间戳
Date.prototype.getTime = function(){return 1672931693};
Math.random = function(){return 0.5};

我们也可以通过最终生成的cookie_t 来判断,自己补的环境是不是===浏览器环境

原理很简单,接下来就是如何实践,我们需要补出一份完美的环境头使得这份静态JS执行得到的cookie_t与浏览器执行得到的一致。

因为补环境是一个系统性工作,是有通用套路的,我们可以使用上篇文章提到的补环境框架进行系统性补环境,我们要做的就是根据log输出以及出现的问题不断完善这个框架。

如图,启动框架,上面是我们补的环境头,下面是我们扣的代码,

继续调试,当我们Proxy拦截器拦截到BOM、DOM api的使用时,就会debugger住,我们可以根据 调用栈 去查看是哪行代码使用的浏览器环境,然后再看到框架中模拟的结果是不是跟浏览器一致,如果不一致,则需要补这个环境。

如此往复的补环境,直到最后可以生成cookie_t,判断是否与浏览器本地生成的一致,如果不一致则使用二分法去定位,看是哪个浏览器环境没补好,直到 最终得到正确的cookie_t,这里贴一下最后执行效果图:

这是最后打印的一部分环境检测点

这是取出最终得到的cookie_t

同理,MmEwMD参数的补环境也是一样的逻辑,当环境头补到完美时,在python中执行最终结果文件,即可得到如下结果:

四、补环境与扣代码总结:

对于js逆向来说,这是两种常规且实用的手段,也各有优劣势;

不管使用哪种方式,我们都是先从网站中将加密JS代码扣出,然后再选择是继续扣代码,将使用到的浏览器环境api进行逻辑替换;还是使用补环境,让加密JS代码仿佛在浏览器环境中运行。

  • 扣代码与补环境都依赖对JS的熟练度,扣代码更侧重js语法和代码逻辑,补环境更侧重原型链及BOM、DOM对象的模拟。
  • 扣代码熟练度依赖逆向经验,补环境几乎只依赖JS熟练度。
  • 扣代码需要调试跟踪大量逻辑,对于rs,如果不解混淆的话,屁股得坐出痔疮;
  • 扣代码需要替换环境检测逻辑,所以也需要知道哪里使用了浏览器环境; 补环境框架可以只用于监测浏览器环境的使用,可以当做扣代码的一个辅助工具。
  • 由于瑞数是动态的,扣代码只能扣一份静态的,所以需要找到vm中使用到的所有动态属性进行映射。而补环境是通用的,补的越多,可通杀的网站就越多。
  • 扣代码比补环境执行效率高,毕竟补环境的代码数比扣代码多很多,可以通过剔除不需要的环境来缩小差距;
  • 扣代码人工耗时远高于补环境。

总而言之,扣代码侧重js语法和代码逻辑,其熟练度依赖于逆向经验,对不同网站要扣的不一样,难以通用,人工效率低,但是程序执行效率高。

补环境侧重原型链及浏览器环境模拟,熟练度几乎只依赖对JS的原理掌握程度,对于不同网站补的越多可通杀的网站越多,人工效率巨高,但是程序执行效率不高。

五、弯道超车环节

过瑞数几乎是每个新手逆向者的小目标,也是面试官常见的提问点。通过本篇文章,我们已经了解了 瑞数的流程及破解思路,接下来我们可以尝试自己从头实现一个完善的补环境框架,去纯环境黑盒过瑞数,但是这会花费很长一段时间来进行开发,而且其中有很多重复性工作比较无聊(复制粘贴对比等)。

走快车道:

本文该版本 补环境框架 是基于上篇文章框架进行系统性完善的,目前可以过瑞数这种级别网站,可以说是相当完善了,补了相当多的环境,如果你想省下大量时间、极大提高效率、直接弯道超车的话,可以 微信联系我:dengshengfeng666 付费源码借鉴;

春节优惠价199(节后恢复统一固定价 233),付完直接发框架项目源码(有最新图文readme可直接小白上手),后续有疑问可以直接问我。

或者直接在CSDN私信我。

该版本与上版本改进点:

  1. 优化Proxy13种拦截器,做到了Proxy的极限,并使其能递归代理,支持a.b.c.d.e...级别的深度检测;
  2. 完善最终结果文件.js的调用机制,使其无需改动,能直接用于V8和node调用;
  3. 新增部分BOM、DOM对象,如:XMLHttpRequest,XMLHttpRequestEventTarget等等;
  4. 补全rs用到的所有浏览器环境方法,使其可以黑盒过rs;
  5. 优化调试方式,可以在想断的时候断点,不想断的时候跳过检测;
  6. 增加py直接调用结果文件案例,可以使用python以v8和node方式调用;
  7. 优化readme,图文介绍环境配置及使用方式。

弯道超车,从我做起

该版本框架目录:

本文转载于网络 如有侵权请联系删除

相关文章

  • anaconda和python版本对照表

    大家好,又见面了,我是你们的朋友全栈君。python2python3anaconda2/32.7.153.7.05.3.12.7.153.7.05.3.02.7.143.6.55.2.02.7.143.6.45.1.02.7.143.6.35.0.12.7.133.6.25.0.02.7.133.6.14.4.02.7.133.6.04.3.12.7.133.6.04.3.02.7.123.5.24.2.02.7.123.5.24.1.12.7.113.5.14.1.02.7.113.5.14.0.0下载地址:清华镜像源使用python3要下载anaconda3对应版本使用python2要下载anaconda2对应版本本对照表,对照清华镜像源中的版本文件官方有较新版本,可前往官方下载官方地址:https://repo.anaconda.com/archive/发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/140106.html原文链接:https://javaforall.cn

  • Vue2剥丝抽茧-响应式系统之computed

    Vue2源码从零详解系列文章,还没有看过的同学可能需要看一下之前的,vue.windliang.wang/场景import{observe}from"./reactive"; import{initComputed}from"./state"; importWatcherfrom"./watcher"; constoptions={ data:{ firstName:"wind", secondName:"liang", title:"标题", }, computed:{ name(){ console.log("name我执行啦!"); returnthis.firstName+this.secondName; }, name2:{ get(){ console.log("name2我执行啦!"); return"name2"+this.firstName+this.secondName; }, set()

  • 获取Repeater控件里动态声称的控件的值

    经常上CSDN社区论坛的朋友应该知道在CSDN里面结贴的时候会让你给各个回帖的人一定的分值作为报酬。此时我们不能固定TextBox框的个数,因为回帖的人数是不固定的。而且如果将TextBox控件和单一的回帖人关联则会导致后台代码冗余,也不利于维护和扩展吗,显得不灵活不显示。QQ空间的留言本里面也是类似的情况。当有人给我们留言的时候我们要回复这个留言就点击“回复”就会出现一个TextBox框出来,然后我们填好自己的留言点击“提交”系统就自动提交了我们的留言。一般对这种重复的数据读取我们经常是用Repeater控件来做,而且也能比较灵活得分页,更可贵的是它能够做到动态生成控件。下面我们就来实现类似QQ留言和回复留言的效果。<asp:RepeaterID="Rep"runat="server"> <ItemTemplate> <tableborder="1"width="100%"cellpadding="0"cellspacing="0"&g

  • Redis 容器与配置(5)

    后面是与默认配置的差异,这里稍微解释一下OptionCommentdaemonizeno不以后台服务的形式运行timeout1800将超时时间限定为半小时,默认是不限的logfile"/data/redis6379.log"指定日志的路径databases50将数据库设为50个dir/data/指定存储目录dbfilenamedump6379.rdb指定数据文件名appendfilename"appendonly6379.aof"指定append文件名Note:为什么普通情况下使用redis都是开启后台服务模式,而这里要使用前台模式呢,那是因为,容器化后,必须终结于一个前台进程,否则容器就直接退出了,这涉及容器交互模式运行和后台运行的一些特性挂载本地卷到容器[root@h104x]#pwd /tmp/x [root@h104x]#ls redis6379.conf [root@h104x]#dockerrun--namemyredis-d-v/tmp/x:/dataredisredis-server/data/redis6379.conf a1a

  • 15分钟详解 Python 安全认证的那些事儿~

    /python生产实战安全认证的那些事儿/系统安全可能往往是被大家所忽略的,我们的很多系统说是在互联网上"裸奔"一点都不夸张,很容易受到攻击,系统安全其实是一个复杂且庞大的话题,若要详细讲来估计用几本书的篇幅都讲不完,基于此本篇及下一篇会着重讲解在我们开发系统过程中遇到的一些安全校验机制,希望能起到抛砖引玉的作用,望各位在开发过程中多多思考不要只局限于功能实现上,共勉~在系统安全、身份验证以及权限授权方面通常来说有各种各样的处理方式,但大多都比较复杂。在很多框架和系统里,涉及安全和身份验证的工作往往都比较繁琐,并且代码量也巨大,基于此也出现了一些相关的协议和相关库我们今天就一起来了解一下相关的内容注意:本文会涉及到经过云解析以及https的SSL证书相关内容1常见认证规范/协议1.1OAuth2OAuth2是一种协议规范,定义了几种用来身份验证和权限授权的处理方式。它是一种可扩展的协议规范,涵盖了几种复杂的使用场景。并且包含了基于第三方身份验证的处理方法。我们常见的"使用微信登陆"、"使用QQ登陆"等第三方登陆方式的底层技术就

  • MQ 系列之 ActiveMQ 消息持久化机制

    1.1简介1.1.1概述  为了避免意外宕机以后丢失信息,需要做到重启后可以恢复消息队列,消息系统一般都会采用持久化机制。ActiveMQ的消息持久化机制有JDBC,AMQ,KahaDB和LevelDB,无论使用哪种持久化方式,消息的存储逻辑都是一致的。就是在发送者将消息发送出去后,消息中心首先将消息存储到本地数据文件、内存数据库或者远程数据库等再试图将消息发送给接收者,成功则将消息从存储中删除,失败则继续尝试发送。消息中心启动以后首先要检查指定的存储位置,如果有未发送成功的消息,则需要把消息发送出去。 1.1.2配置文件1.2持久化方式1.2.1AMQ【了解】☞概述  AMQ是一种文件存储形式,它具有写入速度快和容易恢复的特点。消息存储在一个个文件中,文件的默认大小为32M,当一个存储文件中的消息已经全部被消费,那么这个文件将被标识为可删除,在下一个清除阶段,这个文件被删除。AMQ适用于ActiveMQ5.3之前的版本,主要的缺点是AMQMessage会为每一个Destination创建一个索引,如果使用了大量的Queue,索引文件的大小会占用很多磁盘空间。而且由于索引巨大,一旦B

  • jvm详解——第二篇Jvm垃圾回收机制详解

    以下文章来源于开发者技术前线,作者wingjay1、什么是Jvm堆内存堆是在JVM启动时创建的,主要用来维护运行时数据,如运行过程中创建的对象和数组都是基于这块内存空间。Java堆是非常重要的元素,如果我们动态创建的对象没有得到及时回收,持续堆积,最后会导致堆空间被占满,内存溢出。因此,Java提供了一种垃圾回收机制,在后台创建一个守护进程。该进程会在内存紧张的时候自动跳出来,把堆空间的垃圾全部进行回收,从而保证程序的正常运行。2、那什么是垃圾呢?所谓“垃圾”,就是指所有不再存活的对象。常见的判断是否存活有两种方法:引用计数法和可达性分析。1.引用计数法为每一个创建的对象分配一个引用计数器,用来存储该对象被引用的个数。当该个数为零,意味着没有人再使用这个对象,可以认为“对象死亡”。但是,这种方案存在严重的问题,就是无法检测“循环引用”:当两个对象互相引用,即时它俩都不被外界任何东西引用,它俩的计数都不为零,因此永远不会被回收。而实际上对于开发者而言,这两个对象已经完全没有用处了。因此,Java里没有采用这样的方案来判定对象的“存活性”。2.可达性分析这种方案是目前主流语言里采用的对象存

  • Python vtk学习(1)

    Vtk,(visualizationtoolkit)是一个开源的免费软件系统,主要用于三维计算机图形学、图像处理和可视化。Vtk是在面向对象原理的基础上设计和实现的,它的内核是用C++构建的,包含有大约250,000行代码,2000多个类,还包含有几个转换界面,因此也可以自由的通过Java,Tcl/Tk和Python各种语言使用vtk。以下介绍VTK对于STL图像的基本操作基础概念数据源resource:cone=vtk.vtkConeSource() 映射器mapper:coneMapper=vtk.vtkPolyDataMapper() 映射器添加数据源:coneMapper.SetInput(cone.GetOutput()) 演员actor:coneActor=vtk.vtkActor() 演员添加映射器:coneActor.SetMapper(coneMapper) 绘制器renderer:vtk.vtkRenderer() 绘制器添加演员:renderer.AddActor(coneActor) 绘制窗口win:vtk.vtkRenderWindow() 绘制窗口添加绘制器

  • iOS多设备适配简史以及相应的API支撑实现

    远古的iPhone3和iPhone4时代,设备尺寸都是固定3.5inch,没有所谓的适配的问题,只需要用视图的frame属性进行硬编码即可。随着时间的推移,苹果的设备种类越来越多,尺寸也越来越大,单纯的frame已经不能简单解决问题了,于是推出了AutoLayout技术和SizeClasses技术来解决多种设备的适配问题。一直在做iOS开发的程序员相信在下面的两个版本交界处需要处理适配的坎一定让你焦头烂额过:iOS7出来后视图控制器的根视图默认的尺寸是占据整个屏幕的,如果有半透明导航条的话也默认是延伸到导航栏和状态栏的下面。这段时间相信你对要同时满足iOS7和以下的版本进行大面积的改版和特殊适配处理,尤其是状态栏的高度问题尤为棘手。iOS11出来后尤其是iPhoneX设备推出,iPhoneX设备的特殊性表现为顶部的状态栏高度由20变为了44,底部还出现了一个34的安全区,当横屏时还需要考虑左右两边的44的缩进处理。你需要对所有的布局代码进行重新适配和梳理以便兼容iPhoneX和其他设备,这里面还是状态栏的高度以及底部安全区的的高度尤为棘手。个人认为这两个版本的发布是iOS开发人员遇到的

  • 一文快速上手Logstash

    Elasticsearch是当前主流的分布式大数据存储和搜索引擎,可以为用户提供强大的全文本检索能力,广泛应用于日志检索,全站搜索等领域。Logstash作为Elasicsearch常用的实时数据采集引擎,可以采集来自不同数据源的数据,并对数据进行处理后输出到多种输出源,是ElasticStack的重要组成部分。本文从Logstash的工作原理,使用示例,部署方式及性能调优等方面入手,为大家提供一个快速入门Logstash的方式。文章最后也给出了一些深入了解Logstash的的链接,以方便大家根据需要详细了解。Logstash简介1Logstash工作原理1.1处理过程Logstash处理过程如上图,Logstash的数据处理过程主要包括:Inputs,Filters,Outputs三部分,另外在Inputs和Outputs中可以使用Codecs对数据格式进行处理。这四个部分均以插件形式存在,用户通过定义pipeline配置文件,设置需要使用的input,filter,output,codec插件,以实现特定的数据采集,数据处理,数据输出等功能(1)Inputs:用于从数据源获取数据,

  • 06-搭建master集群

    部署高可用kubernetesmaster集群kubernetesmaster节点包含的组件:kube-apiserverkube-schedulerkube-controller-manager目前这三个组件需要部署在同一台机器上。kube-scheduler、kube-controller-manager和kube-apiserver三者的功能紧密相关;同时只能有一个kube-scheduler、kube-controller-manager进程处于工作状态,如果运行多个,则需要通过选举产生一个leader;本文档现只记录部署一个master节点集群步骤。(后续创建一个有三个master节点的高可用集群,使用loadbalancer来代理访问kube-apiserver的请求,敬请期待~)TLS证书文件pem和token.csv证书文件我们在之前的步骤中已经创建过了,我们再检查一下。#ls/etc/kubernetes/ssl admin-key.pemadmin.pemca-key.pemca.pemkube-proxy-key.pemkube-proxy.pemkubernet

  • XDM,JS如何函数式编程?看这就够了!(一)

    theme:channing-cyan盲猜一个:如果你有看过《medium五万赞好文-《我永远不懂JS闭包》》 《“类”设计模式和“原型”设计模式——“复制”和“委托”的差异》 这两篇文章,你一定会对JS的【函数】有更多兴趣!如果你没兴趣?那我走?皮一下,很舒服~没错!JS就是轻量级的函数式编程!拆解一下这句话,品味一下~本瓜将借助《JavaScript轻量级函数式编程》一书带领你先透析它的落脚点函数式编程,然后再看看JS为什么被称为是“轻量的”!此篇是《JS如何函数式编程?看这就够了!》系列的第一篇,点赞?关注?持续追踪!FP概览重要性函数式编程(FP),不是一个新的概念,它几乎贯穿了整个编程史。直到最近几年,函数式编程才成为整个开发界的主流观念。函数式编程有完善且清晰的原则,一旦我们知道这些原则,我们将能更加快速地读懂代码,定位问题。这是为什么函数式编程重要的原因!比如:你可能写过一些命令式的代码,像if语句和for循环这样的语句。这些语句旨在精确地指导计算机如何完成一件事情。而声明式代码,以及我们努力遵循函数式编程原则所写出的代码,更专注于描述最终的结果。函数式编程以另一种方式来

  • 腾讯云域名注册域名证书下载

    操作场景本文档指导您下载域名注册成功且注册局命名审核通过后自动生成的域名证书。该域名证书可证明该域名归您所有。注意命名审核未通过不能下载证书。腾讯云仅支持下载域名证书电子版,不提供邮寄纸质域名证书服务,若您需纸质域名证书,请您下载后自行打印。操作步骤1.登录腾讯云域名注册控制台,进入“我的域名”页面,查看已购买的所有域名信息。2.在待下载域名证书的域名行中,单击更多>下载域名证书。如下图所示:n3.在弹出的“域名证书”窗口中,单击下载证书,选择下载路径,保存证书。如下图所示:说明如需打印证书,请单击打印证书即可。不同注册商的域名证书不一致,下图展示的是注册商为DNSPod的域名证书。

  • 腾讯云智能培练机器人前期准备

    新增员工 单个新增登录 腾讯云智能培训Web端,选择企业管理>员工管理>新增,填写员工信息,选择角色,单击保存即可新增员工。 批量新增员工登录 腾讯云智能培训Web端,选择企业管理>员工管理>导入,下载模板后,按模板格式要求编辑员工信息,并导入,即可批量新增员工。准备培训资料课程学习支持文件、图片、音频、视频等类型的学习资料。文本考试选择题、判断题、填空题等文本试题、需按题库导入模版准备资料内容。人机对练人机对练试题分为一问一答、情景对话两种学习模式,需按人机对练导入模版准备资料内容。导入模板参考:一问一答题库导入模版、情景对话题库导入模版。

  • 五年老Android,我决定学习后端开发了!

    声明下此文仅是作者从事Android开发再到学习后端的一些见解和经历仁者见仁智者见智! 今天给大家分享一些移动端(Android)开发学习后端开发(JavaWeb)的一些事儿,不知道从什么时候开始身边的同事都开始陆陆续续的在朋友圈发一些后端的文章如:Nginx、Docker、k8s类的知识,后来才发现大家都在学习一些后端的开发工作,可能是感觉移动端技术有些腻了了吧! 甚至还有个iOS同事有在业余时间学习Java、Servlet、Spring等后端知识,这让我深有感触我在学校期间也学过JavaWeb的知识后来因为Android能够做一些界面元素好玩,容易带来成就感,再加上当时的Android真是火到天际。 大概在16年的时候,我就有意无意的在开始自己学习后端知识了,那时候我的工作主要还是做App,偶尔学习下后端知识,可惜的是当时工作的单位后端是用的Python技术栈,由于当时我比较钟情于Java,所有没有学习Python~~。 到了18年,我入职一家二线互联网公司还是做Android开发工作,当前公司正处于业务高速发展期扩张很快,当然变化也有多。当时就感觉移动端的开发人员在各种技术会

  • C#与.net 入门

    C#语言和.NETFramework介绍 https://docs.microsoft.com/zh-cn/dotnet/csharp/getting-started/introduction-to-the-csharp-language-and-the-net-framework C#语言介绍 https://docs.microsoft.com/zh-cn/dotnet/csharp/tour-of-csharp/index C#历代版本特性 https://docs.microsoft.com/zh-cn/dotnet/csharp/whats-new/csharp-version-history 每天成就一小步,积累下来就是一大步。 转发本文请注明出处,谢谢您的阅读与分享!

  • 策略和计费控制(PCC)系统研究

    策略和计费控制(PCC)系统研究 研究内容 [TOC"float:left"] 策略与计费控制(PCC)框架[1] ![架构图](achitecture.png"Architecture""width:800px;float:center") 绑定机制 绑定机制过程包含三个步骤: 会话绑定(SessionBinding) 即将AF会话信息和相应PCC规则关联到一个IP-CAN会话上。PCRF执行会话绑定功能,需要考虑下面的IP-CAN参数: UE的IP地址 UE的标 UE所访问PDN网络的信息。 如果UE标识信息存在,UE标识是与特定IP-CAN中相同类型的UE标识。特别指出IP-CAN网络中UE标识和应用级UE标识可能是不同类型,PCRF需要维护、或可访问两个标识之间的映射关系。这样的映射关系属于其它规范的内容。在本研究报告中假定只支持Rx会话和IP-CAN会话之间是1:1映射关系。 PCC规则授权 即为IP-CAN会话的PCC规则选择QoS参数(QCI、GBR,MBR等).PCRF为IP-CAN会话的动态PCC规则执行PCC规则授权功能。需要考虑特定IP-C

  • Codeforces Round #603 (Div. 2) D. Secret Passwords 并查集

    D.SecretPasswords Oneunknownhackerwantstogettheadmin'spasswordofAtForcestestingsystem,togetproblemsfromthenextcontest.Toachievethat,hesneakedintotheadministrator'sofficeandstoleapieceofpaperwithalistofnpasswords—strings,consistsofsmallLatinletters. HackerwenthomeandstartedpreparingtohackAtForces.Hefoundthatthesystemcontainsonlypasswordsfromthestolenlistandthatthesystemdeterminestheequivalenceofthepasswordsaandbasfollows: twopasswordsaandbareequivalentifthereisaletter,thatexistsinbothaandb; twopa

  • 【PostgreSQL-9.6.3】进程及体系结构

    本文主要讲述了PG的几个主要进程,以及PG的核心架构。进程和体系结构详见下图: 从上面的体系结构图可以看出来,PG使用经典的C/S架构,进程架构。在服务器端有主进程、服务进程、子进程、共享内存以及文件存储几大部分,下面着重讲述服务器端的进程部分: 1.Postmaster主进程和服务进程 当PG数据库启动时,首先会启动Postmaster主进程。这个进程是PG数据库的总控制进程,负责启动和关闭数据库实例。实际上Postmaster进程是一个指向postgres命令的链接,如下: [postgres@drz~]$ll/opt/postgresql/bin/postmaster lrwxrwxrwx.1postgresdba8Aug723:33/opt/postgresql/bin/postmaster->postgres复制 当用户和PG数据库建立连接时,要先与Postmaster进程建立连接,此时客户端进程会发送身份验证消息给Postmaster主进程,Postmaster主进程根据消息进行身份验证,验证通过后,Postmaster主进程会fork出一个会话服务进程为这个用

  • 解决wireshark检测不到网卡的问题

    第一步 1、打开windows设备管理器。 2、查看-显示隐藏的设备 3、非即插即用驱动程序 4、NetGroupPacketFilterDriver右键属性---驱动程序---启动类型,修改类型为“系统”   第二步:  在cmd下输入netstartnpf,打开网络抓包服务   第三步: 运行wireshark,此时网卡已经可以正常检测到了    

  • TCP,UDP,HTTP,IP,SOCKET

    近日对各网络协议进行了一番学习,宏观认识上有收获。 网络由下往上分为物理层、数据链路层、网络层、传输层、会话层、表示层和应用层。(引用)IP协议对应于网络层,TCP/UDP协议对应于传输层, HTTP协议对应于应用层, SOCKET则是对TCP/IP协议的封装和应用。 TCP连接的三次握手:第一次握手:客户端发送syn包(syn=j)到服务器,并进入SYN_SEND状态,等待服务器确认; 第二次握手:服务器收到syn包,必须确认客户的SYN(ack=j+1),同时自己也发送一个SYN包(syn=k),即SYN+ACK包,此时服务器进入SYN_RECV状态;第三次握手:客户端收到服务器的SYN+ACK包,向服务器发送确认包ACK(ack=k+1),此包发送完毕,客户端和服务器进入ESTABLISHED状态,完成三次握手。  握手过程中传送的包里不包含数据,三次握手完毕后,客户端与服务器才正式开始传送数据断开连接时服务器和客户端均可以主动发起断开TCP连接的请求,断开过程需要经过“四次握手”TCP是面向链接的,虽然说网络的不安全不稳定特性决定了多少次握手都不能

相关推荐

推荐阅读