Based
Langchain
llama_index >=0.6.5
GPT-3.5
websockets
python >=3.10
dependence
1 | pip install llama-index |
What use
Supporting private knowledge base AI question-answering chatbot, capable of both knowledge-based Q&A and casual conversation.
more >>
分享个人经验见解
Langchain
llama_index >=0.6.5
GPT-3.5
websockets
python >=3.10
dependence
1 | pip install llama-index |
Supporting private knowledge base AI question-answering chatbot, capable of both knowledge-based Q&A and casual conversation.
more >>随着OPENAI开放API接口后,各大厂商的AI如雨后春笋般涌现,如同十年前的互联网大火,未来的风口必然是在AI上。
当然,基于自训模型/自研AI 门槛过高,不是个人或中小厂能干的,而且即使有也与OPENAI差距不小,因此一般人能卷的也只有应用层了。
基于此背景,我开始研究基于GPT的自定义数据索引问答机器人,接着我发现了llama_index和langchain这两个框架,在此记录一下它的使用方法。
langchain: GitHub - hwchase17/langchain: ⚡ Building applications with LLMs through composability ⚡
最初我尝试使用OPENAI的模型微调,我试着弄了几百KB的文本数据喂进去,然而发现当我使用微调模型对话时AI的回复总是只言片语连一句完整的句子都无法返回。
通过搜索资料后我意识到模型微调不是几百或者几兆文本数据就能达到我想要的目地的。
最终我发现llama_index + langchain可以实现想要的效果
安装python3.10以上版本
安装依赖库:
pip install llama-index
pip install openai
pip install langchain
pip install pandas
准备OPENAI的API KEY
准备好机器人要回答的资料库,可以有PDF、HTML、WORD文档、SQL、API接口甚至GITHUB、WIKI等网络资源也可以,在本章我将使用简单的TXT文本,举例大概内容如下:
塞尔达传说:王国之泪什么时候出? 《塞尔达传说:王国之泪》将于2023年5月12日发售哦,敬请期待!
more >>前面使用Jenkins+docker+shell脚本可以方便的实现单体应用部署,但如果是微服务架构,工程包较多,若是为每一个服务都建一个Jenkins job 会变得很繁琐,这个时候就需要用到docker-compose 容器编排工具,它可以只需一行命令就能帮我们完成多个服务的构建、推送、重启。
考虑到如果有多个服务需要部署到多台服务器,如果每台服务器都采用发送jar包再构建镜像的方式会产生许多重复工作,因此这种情况应该使用jenkins构建镜像->推送到私库->服务器拉取->docker-compose启动 如此流程来完成部署。
需要安装如下软件:
Jenkins (包括git/svn、publish over ssh 这个插件,jenkins安装教程很多此处不再赘述)
docker
Node JS (可选,仅部署前端vue项目时需要安装)
docker compose
准备工作指路:
jenkins: https://www.jenkins.io/download/ 直接启动war包或者使用docker安装
docker: Install Docker Desktop on Linux
Node Js:Node.js
docker compose: GitHub - docker/compose: Define and run multi-container applications with Docker
或者直接使用curl下载安装,以CentOs为例执行如下代码:
1 | 1、下载docker-compose |
为了使服务一次打包多次部署,需要安装docker私库来保存镜像
首先建好映射目录的文件夹:
1 | mkdir /data/registry |
执行docker命令启动私库镜像:
1 | docker run -itd -v /data/registry:/var/lib/registry -p 5000:5000 --restart=always --name registry registry:latest |
添加docker配置:
注意:如果是通过内网访问就配内网IP否则 配公网IP
vi /etc/docker/daemon.json
添加如下:
1 | "insecure-registries": ["192.168.2.200:5000"] |
如果需要设置账号密码:
1 | docker run --rm --entrypoint htpasswd httpd:2 -Bbn yourUserName yourPwd >> ./auth/htpasswd |
一般在内网环境部署私库,拉取推送也是全程内网,所以可装可不装
默认私库无法删除镜像,执行如下命令添加配置:
1 | sudo docker exec -it registry /bin/sh |
网上的资料比较杂,且少有成体系的资料,因此收集资料并按照自己的理解做了一下整合,本文为自我理解与总结,不代表标准答案。
java从编写’System.out.println(“hello world”)’ 开始,并编译运行,在这期间到底发生了什么。
一个.java文件的完整周期是 java编码成jvm可识别的.class文件, 然后大致流程是: 加载–>连接–>初始化–>使用–>卸载
1、通过全类名获取定义此类的二进制字节流(类似反射)
2、将字节流所代表的静态存储结构转换为JVM方法区的运行时数据结构
3、在内存中生成一个代表该类的 java.lang.Class 对象,作为方法区这些数据的访问入口(这样代码才能通过全类名访问到该对象)
PS:数组类型不通过类加载器创建,它由JAVA虚拟机直接创建,数组的加载可通过自定义类加载器控制加载方式
JVM中有三个类加载器,除了 BootstrapClassLoader 其他类加载器均由 Java 实现且全部继承自java.lang.ClassLoader
1、BootstrapClassLoader(启动类加载器) :最顶层的加载类,由 C++实现,负责加载 %JAVA_HOME%/lib目录下的 jar 包和类或者被 -Xbootclasspath参数指定的路径中的所有类。
2、ExtensionClassLoader(扩展类加载器) :主要负责加载 %JRE_HOME%/lib/ext 目录下的 jar 包和类,或被 java.ext.dirs 系统变量所指定的路径下的 jar 包。
3、AppClassLoader(应用程序类加载器) :面向我们用户的加载器,负责加载当前应用 classpath 下的所有 jar 包和类。
适用于单库,日志表过大的问题,如每月产生几千万条日志,还不能清理,必须存档,其它业务表反而没这么大量时,可以使用分表来解决。
可以按实际情况来决定是按年分表还是按月分表,每年产生的数据量过亿时可以按月分表。
使用spring boot 2.x + mybatis-plus + shardingjdbc5.x + druid
shardingjdbc非常坑的一个点,每个版本变一次配置,官方文档写得不清不楚,通过GITHUB找到官方示例,发现示例也很少,最后是通过网上的博文+示例+文档才搞定。
1 | <properties> |
此文章为个人经验总结,纯当自用笔记(反正也没人看),每个人的体质和情况各不相同,不保证对每个人都有效。
某伟人曾说过:身体是革命的本钱,钱没了还可以再嫌,人病了那就人财两空了。
口腔溃疡一般是由于饮食不均衡导致的,在外漂泊的打工人多数没有条件自己做饭,吃外卖又容易营养不均衡,解决办法如下:
自此以后再也不怕口腔溃疡啦!
more >>在之前的文章:使用左右值树形数据结构实现树形菜单 中记录了如何使用左右值增删改查节点,本次将记录一下如何移动节点,语言使用JAVA + MYSQL实现。
总体思路
移动节点的大致思路是记录移动节点和目标节点之间的左右值以及其子节点的左右值,移动节点及其子节点左右值和目标节点及其子节点的左右值相互加减。
举例
节点A的左右值是LEFT=1,RIGHT=2,节点B的左右值是LEFT=5,RIGHT=6,现在要将节点A移动到节点B前面,那么它的移动范围就是RIGHT - LEFT + 1,即:2 - 1 +1 = 2,也就是说节点A左右值+2,左右值小于节点B的左右值-2 。
结果:节点A的LEFT = 3 ,RIGHT = 4,节点B前面的节点左右值减了2变成了LEFT=1,RIGHT=2,相当于和节点A换了个位置,如此来达到移动节点的目的
后续的移动到节点B后面、移动到节点B作为其子节点思路相同。
更新
2021-6-22 更新
修复了BUG,最新代码请关注: https://github.com/reinershir/lui-auth 以下代码摘抄自菜单管理功能
more >>在前一章记录了如何使用netty作为TCP通信的服务端:点击前往 ,本章记录一下如何解决硬件设备在接收到服务端发送过来的消息时有连包的问题。
在通过监测硬件的收包信息时发现偶尔会出现心跳包和指令“粘”在一块的情况,例如指令的发送内容是:EEFF0103GGHH,心跳包的回复是:EEFF0201GGHH。
当心跳包返回信息的时候此时正好指令下发,那么设备端就会收到:EEFF0103GGHHEEFF0201GGHH。
这是由于调用netty的writeAndFlush()方法时并不是马上将数据发送过去,而将它放在一个缓冲池当中,而由于硬件的一发一收通信机制客户端无法对连包的数据做分割,因此这个问题要由服务端解决。
HTTP属于应用层协议,TCP属于传输层协议,IP属于网络层协议,一个HTTP协议由IP协议包体包含了TCP协议内容,而TCP协议包体又包括了HTTP协议内容,就像一个洋葱。
一个HTTP请求的完整历程,首先会根据URL解析请求的地址和端口,此时的地址拿到的一般是域名,因此还需要根据DNS服务器获取域名的真实IP。
NDS服务查询完毕后,此时浏览器会调用Socket库将HTTP协议里的内容包装成TCP或者UDP协议包。
光靠TCP协议还无法具备传输功能,因此TCP还需要借助IP协议来定位目标服务器在互联网中的位置,光靠IP依旧无法准确定位,因为一个IP可能有好几台设备使用,要明确要传输的目标还得在IP头部加上目标的MAC地址。
最后由网卡将数字信息转换为光信号经网线发送出去,将服务器通过交换机和路由器接收到请求包后像剥洋葱一样一层一层解析包中内容。
小结,一个HTTP请求总共要经历如下几层协议:
应用层:定义数据格式,并按照对应的格式解读数据。 –HTTP
传输层:定义端口,确认主机上应用程序的身份,并将数据包交给对应的应用程序。 –TCP
网络层:定义IP地址,确认主机所在的网络位置,并通过IP进行MAC寻址,对外网数据包进行路由转发。 –IP
链路层:对0和1进行分组,定义数据帧,确认主机的物理地址,传输数据。 –物理传输
最近看了《白帽子讲WEB安全》,书的内容可能已经过时了,但是用来提高安全意识还是不错的,现在将它记下来做个总结。
WEB安全整体给我的感觉是虽然重要,但攻击手段有限,安全的大头还是在服务器安全这块。
先来第一个,XSS攻击,XSS攻击主要分为两类: 1、存储型XSS 2、反射型XSS ,先来看反射型XSS攻击。
所谓反射型XSS攻击其实就是利用JAVASCRIPT解析漏洞,将原本该解析成HTML的内容解析成了JS代码,那么如何实现攻击的呢? 假设某个20年前原始的网站有如下代码:
1 | 请输入搜索关键字:<input type="text" name="search" > |
此时我们输入:<script>alert('xss')</script> ,点击搜索后,发现页面上打印alert(xss)了,但是这样只是控制了自己的浏览器JS,没有意义(用浏览器控制台一样可以做到),因此要将此漏洞散布出去。
假设它的搜索请求url是:http://reiner.host/search?keyword=WEB安全总结 ,将其改为 http://reiner.host/search?keyword= ,并将链接分享出去,诱导别人去点击。
此时这个倒霉鬼如果刚好登陆了该网站,那么你就可以通过JS拿到他的sessionId,然后弄个不可见的iframe将sessionId传到自己的服务器,从而为所欲为了。
PS:担心加上JS代码后链接过长可以弄个短链接。
所以防止反射型XSS的关键点在于不能直接将用户输入的内容展现出来,绝大部分前端框架一般是解决了此问题的,即用户输入内容不会被浏览器解析为JS代码,但不排除一定就没有XSS漏洞了。
防反射型XSS攻击总结
1、对于用户输入的内容不要直接展示
2、使用稳定的开源框架,一般有自动处理
这就是为什么要注意不要乱点链接
more >>tag:
缺失模块。
1、请确保node版本大于6.2
2、在博客根目录(注意不是yilia-plus根目录)执行以下命令:
npm i hexo-generator-json-content --save
3、在根目录_config.yml里添加配置:
jsonContent:
meta: false
pages: false
posts:
title: true
date: true
path: true
text: false
raw: false
content: false
slug: false
updated: false
comments: false
link: false
permalink: false
excerpt: false
categories: false
tags: true