K8S对接Ceph分布式存储

ops/2024/9/20 1:15:33/ 标签: kubernetes, ceph, 容器

文章目录

    • 一、Ceph理论知识
      • 1、Ceph简介
      • 2、Ceph分布式存储的优点
      • 3、Ceph核心组件
    • 二、部署Ceph高可用集群
      • 1、服务器环境信息
      • 2、部署前环境准备工作
      • 3、部署Ceph监控服务Monitor
      • 4、激活Ceph存储服务OSD
    • 三、K8S对接Ceph存储
      • 1、K8S对接Ceph RBD实现数据持久化
      • 2、基于Ceph RBD生成PV
      • 3、基于Storageclass动态生成PV
      • 4、K8S对接CephFS实现数据持久化
    • 四、所遇问题记录
      • 1、激活OSD失败

一、Ceph理论知识

1、Ceph简介

Ceph 是一个开源的分布式存储系统,用于提供高性能、高可靠性的对象存储、块存储和文件系统,它通过去中心化的架构,自动处理数据复制和恢复,旨在提供弹性扩展和容错能力。Ceph官方网址:

Ceph包含一下几种存储类型:

(1)块存储(RBD):

  • 用途: 提供了高性能的块级存储,类似于传统的磁盘驱动器。通常用于虚拟机的存储或数据库的存储。

  • 接口: 通过 Ceph 的 RADOS(Reliable Autonomic Distributed Object Store)接口提供块设备。

  • 架构: 在 Ceph 集群中,每个块设备映射到一个 RADOS 对象,支持动态分配和快照功能。

  • 扩展性: 可以根据需求动态增加或减少存储容量。

  • 缺点:块设备具有优异的读写性能,但不能多处挂载同时读写,目前主要用在OpenStack上作为虚拟磁盘。

  • 总结:块设备可理解成一块硬盘,用户直接使用不含文件系统的块设备,也可以将其格式化成特定的文件系统,由文件系统来组织管理存储空间,从而为用户提供丰富而友好的数据操作支持。

(2)文件系统(CephFS):

  • 用途: 提供一个完整的分布式文件系统,用于支持标准的文件操作和目录结构,适用于需要 POSIX 兼容的应用程序。
  • 接口: 提供标准的 POSIX 文件系统接口,允许通过传统的文件系统工具和应用程序访问存储的数据。
  • 架构: CephFS 构建在 Ceph 的对象存储之上,通过元数据服务器(MDS)来管理文件和目录的元数据。
  • 扩展性: 支持横向扩展,能够处理大量的文件和目录操作。
  • 缺点:文件系统接口读写性能较块设备接口差,但具有优异的共享性。

(3)对象存储(Object Gateway):

  • 用途: 主要用于存储大量的非结构化数据,如照片、视频、备份和日志文件。

  • 接口: 提供了兼容 Amazon S3 和 OpenStack Swift 的 RESTful API,方便与现有的云服务和应用程序集成。

  • 架构: 数据以对象的形式存储,每个对象由数据、元数据和唯一标识符(Object ID)组成。

  • 扩展性: 对象存储可以通过增加更多的存储节点来横向扩展,适合大规模数据存储需求。

问题:有了块设备接口存储和文件系统接口存储,为什么还整个对象存储呢?

答:Ceph的块设备存储具有优异的存储性能但不具有共享性,而Ceph的文件系统具有共享性然而性能较块设备存储差,为什么不权衡一下存储性能和共享性,整个具有共享性而存储性能好于文件系统存储的存储呢,对象存储就这样出现了。

2、Ceph分布式存储的优点

  • 弹性扩展: 可以无缝添加更多的存储节点,以支持增长的存储需求,而不会影响系统的性能。
  • 高可用性: 数据自动复制到多个节点,确保在硬件故障时数据不会丢失。
  • 高性能:读写速度快。
  • 去中心化: 没有单点故障,提升了系统的可靠性和容错能力。
  • 灵活性: 支持对象存储、块存储和文件系统等多种存储类型,满足不同的需求。

3、Ceph核心组件

  • Monitors:监视器,负责维护集群状态的映射,包括监视器映射,管理器映射,OSD映射和CRUSH映射。这些映射是Ceph守护进程相互协调所需的关键集群状态。监视器还负责管理守护进程和客户端之间的身份验证。冗余和高可用性通常至少需要三个监视器。
  • Managers:负责跟踪运行时指标和Ceph集群的当前状态,包括存储利用率,当前性能指标和系统负载。 Ceph Manager守护进程还托管基于python的模块来管理和公开Ceph集群信息,包括基于Web的Ceph Dashboard和REST API。高可用性通常至少需要两名Managers。
  • Ceph OSD:负责存储数据,处理数据复制,恢复,重新平衡,并通过检查其他Ceph OSD守护进程来获取心跳,为Ceph监视器和管理器提供一些监视信息。冗余和高可用性通常至少需要3个Ceph OSD。
  • MDS:元数据服务器,代表Ceph文件系统存储元数据(即,Ceph块设备和Ceph对象存储不使用MDS)。 Ceph元数据服务器允许POSIX文件系统用户执行基本命令(如ls,find等),而不会给Ceph存储集群带来巨大负担。

二、部署Ceph高可用集群

1、服务器环境信息

注意:由于我本次仅仅只是实验所以我把Ceph集群与K8S集群部署到了一起,如果生产环境需要多申请三台服务器,单独部署Ceph集群!

序号IP地址主机名磁盘安装服务别名
116.32.15.200master-1sdb-20GK8S-Master、cephceph-deployK8S管理节点、Ceph管理节点
216.32.15.201node-1sdb-20GK8S-Node-1、ceph
316.32.15.202node-2sdb-20GK8S-Node-2、ceph

2、部署前环境准备工作

PS:所有主机中执行

1、配置阿里云Ceph安装源

cat >>  /etc/yum.repos.d/ceph.repo  << EOF
[Ceph] 
name=Ceph packages for \$basearch
baseurl=http://mirrors.aliyun.com/ceph/rpm-jewel/el7/x86_64/ 
enabled=1 
gpgcheck=0 
type=rpm-md 
gpgkey=https://mirrors.aliyun.com/ceph/keys/release.asc 
priority=1
[Ceph-noarch] 
name=Ceph noarch packages 
baseurl=http://mirrors.aliyun.com/ceph/rpm-jewel/el7/noarch/ 
enabled=1 
gpgcheck=0 
type=rpm-md 
gpgkey=https://mirrors.aliyun.com/ceph/keys/release.asc 
priority=1 
[ceph-source]
name=Ceph source packages 
baseurl=http://mirrors.aliyun.com/ceph/rpm-jewel/el7/SRPMS/ 
enabled=1 
gpgcheck=0 
type=rpm-md 
gpgkey=https://mirrors.aliyun.com/ceph/keys/release.asc 
priority=1
EOF

2、安装基础包,平时排查问题需要用到

yum install -y yum-utils device-mapper-persistent-data lvm2 wget net-tools nfs-utils lrzsz gcc gcc-c++ make cmake libxml2-devel openssl-devel curl curl-devel unzip sudo ntp libaio-devel wget vim ncurses-devel autoconf automake zlib-devel  python-devel epel-release openssh-server socat  ipvsadm conntrack ntpdate telnet deltarpm

3、添加hosts本地解析

vim /etc/hosts16.32.15.200 master-1
16.32.15.201 node-1
16.32.15.202 node-2

4、修改主机名(对应主机执行)

hostnamectl set-hostname master-1 && bash
hostnamectl set-hostname node-1 && bash
hostnamectl set-hostname node-2 && bash

5、配置内网免密登入

ssh-keygenssh-copy-id master-1
ssh-copy-id node-1
ssh-copy-id node-2

6、配置NTP时间同步

yum -y install ntpdate
ntpdate ntp1.aliyun.com

添加定时任务,每天凌晨1点自动同步时间

echo "0 1 * * * ntpdate ntp1.aliyun.com" >> /var/spool/cron/root

3、部署Ceph监控服务Monitor

1、安装ceph-deploy(Ceph管理节点执行)

yum install python-setuptools  ceph-deploy -y

2、安装ceph(所有主机执行)

yum install ceph ceph-radosgw  -y

3、查看ceph版本

ceph --version

4、创建Monitor(Ceph管理节点执行)

创建一个目录,用于保存 ceph-deploy 生成的配置文件信息的

cd /etc/ceph
ceph-deploy new master-1 node-1 node-2

查看当前生成的文件:

ls -1 /etc/cephceph.conf   				# Ceph配置文件
ceph-deploy-ceph.log		# 日志文件
ceph.mon.keyring			# Monitor密钥

5、修改ceph配置文件(Ceph管理节点执行)

vim /etc/ceph/ceph.conf[global]
fsid = 8797ef39-fcb3-4e82-bf49-a068cfc72eae
mon_initial_members = master-1, node-1, node-2
mon_host = 16.32.15.200,16.32.15.201,16.32.15.202
auth_cluster_required = cephx
auth_service_required = cephx
auth_client_required = cephx
# 新增配置如下:
osd_pool_default_size = 2               # 2个osd也能达到active+clean状态
mon clock drift allowed = 0.500         # 监视器间允许的时钟漂移量默认值0.05
mon clock drift warn backoff = 10       # 时钟偏移警告的退避指数。默认值5

注意:Ceph对每个mon之间的时间同步延时默认要求在0.05s之间,这个时间有的时候太短了。所以如果ceph集群如果出现clock问题就检查ntp时间同步或者适当放宽这个误差时间。

6、配置初始Monitor、收集所有的密钥(Ceph管理节点执行)

cd /etc/ceph
ceph-deploy mon create-initial

等待收集完成后,查看收集到的key

ls -1 /etc/ceph/*.keyring

4、激活Ceph存储服务OSD

注意:以下操作均在,Ceph管理节点执行!!

1、准备OSD

cd /etc/ceph/ceph-deploy osd prepare master-1:/dev/sdb
ceph-deploy osd prepare node-1:/dev/sdb 
ceph-deploy osd prepare node-2:/dev/sdb

2、激活OSD

ceph-deploy osd activate master-1:/dev/sdb1
ceph-deploy osd activate node-1:/dev/sdb1
ceph-deploy osd activate node-2:/dev/sdb1

3、查看OSD状态

ceph-deploy osd list master-1 node-1 node-2

三、K8S对接Ceph存储

注意1:在K8S集群中如果使用Ceph存储,需要再K8S各个节点中安装ceph-common工具,安装命令如下:

yum install ceph-common -y

注意2:如果K8S集群和Ceph集群不在相同服务器中,需要把Ceph集群中的 /etc/ceph 目录拷贝到K8S各个节点下!!

1、K8S对接Ceph RBD实现数据持久化

PS:以下操作均在,Ceph管理节、K8S管理节点中执行!!

1、创建RBD

ceph osd pool create k8srbd 16
rbd create rbda -s 1024 -p k8srbd			
rbd feature disable  k8srbd/rbda object-map fast-diff deep-flatten   # 禁用无用特性

2、查看RBD状态信息

ceph osd pool ls				# 列出所有pool
ceph osd pool stats k8srbd		# 查看状态

3、创建Pod,使用RBD挂载

apiVersion: v1
kind: Pod
metadata:name: test-rbd
spec:containers:- image: nginxname: nginximagePullPolicy: IfNotPresentvolumeMounts:- name: testrbdmountPath: /optvolumes:- name: testrbdrbd:monitors: # 监视器IP:Port- '16.32.15.200:6789'- '16.32.15.201:6789'- '16.32.15.202:6789'pool: k8srbd # pool名称image: rbda # image名称fsType: xfsreadOnly: falseuser: adminkeyring: /etc/ceph/ceph.client.admin.keyring

3、执行apply并查看Pod状态

kubectl apply -f pod.yaml
kubectl get pods

注意:RBD类型只能挂载一个,如果再创建一个Pod,使用相同的RBD,则会创建失败!

2、基于Ceph RBD生成PV

PS:以下操作均在,Ceph管理节、K8S管理节点中执行!!

1、创建Ceph secret对象

Secret对象用于K8S Volume插件访问Ceph集群,获取client.admin的keyring值,(ceph管理节点):

ceph auth get-key client.admin | base64
QVFDVHljbG1hU3JnSnhBQSt0eUpmcVRjNEs2SHdrZUcxdjJVblE9PQ==

2、创建Ceph的Secret资源(K8S Master节点操作):

apiVersion: v1
kind: Secret
metadata:name: ceph-secret
data:key: QVFBWk0zeGdZdDlhQXhBQVZsS0poYzlQUlBianBGSWJVbDNBenc9PQ==
kubectl apply -f ceph-secret.yaml

3、创建pool池

ceph osd pool create k8srbd1 16
rbd create rbda -s 1024 -p k8srbd1
rbd feature disable k8srbd1/rbda object-map fast-diff deep-flatten

4、创建PV、PVC

apiVersion: v1
kind: PersistentVolume
metadata:name: ceph-pv
spec:capacity:storage: 1GiaccessModes:- ReadOnlyManyrbd:monitors:- '16.32.15.200:6789'- '16.32.15.201:6789'- '16.32.15.202:6789'pool: k8srbd1image: rbdauser: adminsecretRef:name: ceph-secretfsType: xfsreadOnly: falsepersistentVolumeReclaimPolicy: Recycle
---
kind: PersistentVolumeClaim 
apiVersion: v1 
metadata:   name: ceph-pvc 
spec:   accessModes:     - ReadOnlyMany   resources:     requests:       storage: 1Gi
kubectl apply -f ceph-pv-pvc.yaml

查看PVC是否绑定PV:

kubectl get pvc ceph-pvc

在这里插入图片描述

5、创建Deployment资源,使用PVC

apiVersion: apps/v1
kind: Deployment
metadata:name: nginx-deployment
spec:selector:matchLabels:app: nginxreplicas: 2template:metadata:labels:app: nginxspec:containers:- name: nginximage: nginximagePullPolicy: IfNotPresentports:- containerPort: 80volumeMounts:- mountPath: "/ceph-data"name: ceph-datavolumes:- name: ceph-datapersistentVolumeClaim:claimName: ceph-pvc
kubectl apply -f deployment.yaml

注意:Ceph RBD块存储能在同一个Node上跨pod以使用ReadWriteOnce共享挂载,但不支持跨Node使用。

问题:结合Ceph RBD共享挂载的特性,发现一个问题:

由于Deployment触发更新,为了保证服务的可用性,Deployment要先创建一个Pod并运行正常之后,再去删除老Pod。而如果新创建的Pod和老Pod不在一个node,就会导致此故障。

解决办法:

  • 使用能支持跨node和pod之间挂载的共享存储,例如CephFS,GlusterFS等。
  • 给Node添加Label,只允许Deployment所管理的Pod调度到一个固定的Node上。(不建议,Node节点宕机,服务也就宕机了)

3、基于Storageclass动态生成PV

注意:K8S1.20版本之后如果需要使用自动生成PV,需要修改kube-apiserver配置,进行兼容:

vim /etc/kubernetes/manifests/kube-apiserver.yaml
# 添加这一行:
- --feature-gates=RemoveSelfLink=false

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

重启kubelet生效

systemctl restart kubelet

注意:我这边两套集群v1.26.2版本修改此配置后,导致集群起不来,而v1.23.0版本修改后可以正常启动,建议现在测试环境添加此配置,如果没有问题,在添加生产环境!!

1、执行赋权操作(所有K8S集群、Ceph集群中执行)

chmod 777  -R  /etc/ceph/*
mkdir /root/.ceph/
cp -ar /etc/ceph/ /root/.ceph/
cp -ar /etc/ceph/* /root/.ceph/

2、创建RBD的供应商Provisioner

kind: ClusterRole
apiVersion: rbac.authorization.k8s.io/v1
metadata:name: rbd-provisioner
rules:- apiGroups: [""]resources: ["persistentvolumes"]verbs: ["get", "list", "watch", "create", "delete"]- apiGroups: [""]resources: ["persistentvolumeclaims"]verbs: ["get", "list", "watch", "update"]- apiGroups: ["storage.k8s.io"]resources: ["storageclasses"]verbs: ["get", "list", "watch"]- apiGroups: [""]resources: ["events"]verbs: ["create", "update", "patch"]- apiGroups: [""]resources: ["services"]resourceNames: ["kube-dns","coredns"]verbs: ["list", "get"]
---
kind: ClusterRoleBinding
apiVersion: rbac.authorization.k8s.io/v1
metadata:name: rbd-provisioner
subjects:- kind: ServiceAccountname: rbd-provisionernamespace: default
roleRef:kind: ClusterRolename: rbd-provisionerapiGroup: rbac.authorization.k8s.io
---
apiVersion: rbac.authorization.k8s.io/v1
kind: Role
metadata:name: rbd-provisioner
rules:
- apiGroups: [""]resources: ["secrets"]verbs: ["get"]
- apiGroups: [""]resources: ["endpoints"]verbs: ["get", "list", "watch", "create", "update", "patch"]
---
apiVersion: rbac.authorization.k8s.io/v1
kind: RoleBinding
metadata:name: rbd-provisioner
roleRef:apiGroup: rbac.authorization.k8s.iokind: Rolename: rbd-provisioner
subjects:
- kind: ServiceAccountname: rbd-provisionernamespace: default
---
apiVersion: apps/v1
kind: Deployment
metadata:name: rbd-provisioner
spec:selector:matchLabels:app: rbd-provisionerreplicas: 1strategy:type: Recreatetemplate:metadata:labels:app: rbd-provisionerspec:containers:- name: rbd-provisionerimage: quay.io/xianchao/external_storage/rbd-provisioner:v1imagePullPolicy: IfNotPresentenv:- name: PROVISIONER_NAMEvalue: ceph.com/rbdserviceAccount: rbd-provisioner
---
apiVersion: v1
kind: ServiceAccount
metadata:name: rbd-provisioner
kubectl apply -f rbd-provisioner.yaml

3、创建Ceph Secret

ceph osd pool create k8srbd2 16
ceph auth get-key client.admin | base64
apiVersion: v1
kind: Secret
metadata:name: ceph-secret-1
type: "ceph.com/rbd"
data:key: QVFDVHljbG1hU3JnSnhBQSt0eUpmcVRjNEs2SHdrZUcxdjJVblE9PQ== 
kubectl apply -f ceph-secret-1.yaml

4、创建Storageclass

apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:name: k8s-rbd
provisioner: ceph.com/rbd # 与provisioner对应
parameters:monitors: 16.32.15.200:6789,16.32.15.201:6789,16.32.15.202:6789adminId: adminadminSecretName: ceph-secret-1pool: k8srbd2     userId: adminuserSecretName: ceph-secret-1fsType: xfsimageFormat: "2"imageFeatures: "layering"
kubectl apply -f storageclass.yaml

4、创建PVC,自动生成PV

kind: PersistentVolumeClaim
apiVersion: v1
metadata:name: rbd-pvc
spec:accessModes:- ReadWriteOncevolumeMode: Filesystemresources:requests:storage: 1GistorageClassName: k8s-rbd
kubectl apply -f rbd-pvc.yaml
kubectl get pvc

5、创建Pod,挂载PVC

apiVersion: v1
kind: Pod
metadata:labels:test: rbd-podname: ceph-rbd-pod
spec:containers:- name: ceph-rbd-nginximage: nginximagePullPolicy: IfNotPresentvolumeMounts:- name: ceph-rbdmountPath: /mntreadOnly: falsevolumes:- name: ceph-rbdpersistentVolumeClaim:claimName: rbd-pvc
kubectl apply -f pod-sto.yaml

4、K8S对接CephFS实现数据持久化

PS:以下操作均在,Ceph管理节、K8S管理节点中执行!!

1、创建MDS

ceph-deploy mds create  master-1 node-1 node-2

2、创建存储池

一个CephFS至少要求两个librados存储池,一个为data,一个为metadata。当配置这两个存储池时,需要注意以下两点:

  • 为metadata pool设置较高级别的副本级别,因为metadata的损坏可能导致整个文件系统不用。
  • 建议metadata pool使用低延时存储,比如SSD,因为metadata会直接影响客户端的响应速度。
ceph osd pool create cephfs_data 128
ceph osd pool create cephfs_metadata 128

pg_num 取值是强制性的,因为不能自动计算。下面是几个常用的值:

  • 少于 5 个 OSD 时可把 pg_num 设置为 128
  • OSD 数量在 5 到 10 个时,可把 pg_num 设置为 512
  • OSD 数量在 10 到 50 个时,可把 pg_num 设置为 4096

当OSD 数量大于 50 时,得理解权衡方法、以及如何自己计算 pg_num 取值

自己计算 pg_num 取值时可借助 pgcalc 工具

随着 OSD 数量的增加,正确的 pg_num 取值变得更加重要,因为它显著地影响着集群的行为、以及出错时的数据持久性(即灾难性事件导致数据丢失的概率)

3、创建文件系统

ceph fs new k8sfs cephfs_metadata cephfs_data

4、查看

ceph fs ls              # 查看创建后的cephfs
ceph mds stat           # 查看mds节点状态
ceph -s					# 查看集群信息

5、创建目录,将CephFS挂载到此目录

cat /etc/ceph/ceph.client.admin.keyring |grep key|awk -F" " '{print $3}' > /etc/ceph/admin.secret
mkdir /data/ceph_data -p
mount -t ceph 16.32.15.201:6789:/ /data/ceph_data -o name=admin,secretfile=/etc/ceph/admin.secret
df -hT /data/ceph_data

6、在CephFS挂载目录中,创建子目录,作为存储挂载

mkdir -p /data/ceph_data/qinzt
chmod 0777 /data/ceph_data/qinzt

7、创建Secret,用于K8S连接Ceph

将/etc/ceph/ceph.client.admin.keyring里面的key的值转换为base64,否则会有问题

cat /etc/ceph/ceph.client.admin.keyring|awk NR==2'{print $NF}'|base64
QVFCbExNcG11Q215TEJBQVdWTzlEY2h1T2Zham5GQWxmV1dESFE9PQo=
apiVersion: v1
kind: Secret
metadata:name: cephfs-secret
data:key: QVFCbExNcG11Q215TEJBQVdWTzlEY2h1T2Zham5GQWxmV1dESFE9PQo=
kubectl apply -f cephfs-secret.yaml

8、创建PV、PVC

apiVersion: v1
kind: PersistentVolume
metadata:name: cephfs-pv
spec:capacity:storage: 1GiaccessModes:- ReadWriteManycephfs:monitors:     - '16.32.15.200:6789'- '16.32.15.201:6789'- '16.32.15.202:6789'path: /qinzt  # 挂载目录(Ceph根下的qinzt目录 > /data/ceph_data/qinzt)user: adminreadOnly: falsesecretRef:name: cephfs-secretpersistentVolumeReclaimPolicy: Recycle
---
kind: PersistentVolumeClaim
apiVersion: v1
metadata:name: cephfs-pvc
spec:accessModes:- ReadWriteManyvolumeName: cephfs-pvresources:requests:storage: 1Gi
kubectl apply -f cephfs-pv-pvc.yaml
kubectl get pvc cephfs-pvc

9、创建Pods,挂载CephFS

apiVersion: apps/v1
kind: Deployment
metadata:name: cephfs-deployment
spec:replicas: 3selector:matchLabels:app: nginxenv: devtemplate:metadata:labels:app: nginxenv: devspec:containers:- image: nginxname: nginximagePullPolicy: IfNotPresentvolumeMounts:- name: cephfsmountPath: /mntvolumes:- name: cephfspersistentVolumeClaim:claimName: cephfs-pvc
kubectl apply -f cephfs-deployment.yaml

10、验证,Pod中创建文件,本地查看是否存在

# 进入Pod1创建5个文件
kubectl exec -it cephfs-deployment-6f66847599-2hd9s -- /bin/bash
touch pod1{1..5}.txt /mnt/# 进入Pod2查看创建的文件
kubectl exec -it cephfs-deployment-6f66847599-cggzm -- /bin/bash
ls /mnt/*# 查看本地目录
ls /data/ceph_data/qinzt/
pod11.txt  pod12.txt  pod13.txt  pod14.txt  pod15.txt

通过验证,可以确认容器内挂载目录是共享的,并且Pod写入的数据已经存储到了CephFS中了

四、所遇问题记录

1、激活OSD失败

报错信息:ERROR: error creating empty object store in /var/lib/ceph/tmp/mnt.QdHa3y: (13) Permission denied

解决方案:

chown ceph:ceph /dev/sdb*

http://www.ppmy.cn/ops/102499.html

相关文章

计算机视觉编程 1(图片处理)

目录 灰色度 缩略图 拷贝粘贴区域 调整图像尺寸 旋转图像45 画图线、描点 灰色度 灰度是指图像中每个像素的亮度值&#xff0c;用来描述图像中各个像素的明暗程度。在计算机视觉中&#xff0c;灰度可以通过以下方式来计算&#xff1a; 1. 平均值法&#xff1a;将图像中每…

计算机毕业设计推荐-基于python的个性化旅游路线推荐平台

&#x1f496;&#x1f525;作者主页&#xff1a;毕设木哥 精彩专栏推荐订阅&#xff1a;在 下方专栏&#x1f447;&#x1f3fb;&#x1f447;&#x1f3fb;&#x1f447;&#x1f3fb;&#x1f447;&#x1f3fb; 实战项目 文章目录 实战项目 一、基于python的个性化旅游路线…

ubuntu20 安装ros noetic版本

【ROS】Ubuntu20.04卸载重装ROS_ubuntu20.04卸载ros-CSDN博客 错误处理——rosdep init&#xff0c;rosdep update失败解决方案_rosdep init出错-CSDN博客 ubuntu 20.04解决在处理时有错误发生&#xff1a; /var/cache/apt/archives/python3-catkin-pkg-modules_0.4.24-1_all…

NoSQL数据库-Redis集群详解及案例实现

一、 关系型数据库和 NoSQL 数据库 1.1 数据库主要分为两大类&#xff1a;关系型数据库与 NoSQL 数据库 关系型数据库&#xff0c;是建立在关系模型基础上的数据库&#xff0c;其借助于集合代数等数学概念和方法来处理数据库中的数据主流的 MySQL、Oracle、MS SQL Server 和 D…

基于JAVA的专利资源共享平台

项目介绍 基于JAVA的专利资源共享平台系统是一个集专利信息展示、资源共享、交易服务等功能于一体的综合性平台。该系统利用JAVA语言的强大功能和广泛的生态系统&#xff0c;结合数据库技术、Web开发技术等&#xff0c;为用户提供了一个高效、安全、便捷的专利资源共享和交易环…

【C++】日期和时间

C 提供了多种处理日期和时间的功能&#xff0c;主要通过标准库 <ctime> 和 <chrono> 提供。以下是 C 中处理日期和时间的功能介绍及其用法&#xff1a; 1. <ctime> 库 <ctime> 是 C 中处理时间的传统库&#xff0c;提供了一些基本的时间操作函数。这…

Amazon Bedrock 实践:零基础创建贪吃蛇游戏

本文探讨了如何利用 Amazon Bedrock 和大型语言模型&#xff0c;快速创建经典的贪吃蛇游戏原型代码。重点展示了利用提示工程&#xff0c;将创新想法高效转化为可运行代码方面的过程。文章还介绍了评估和优化提示词质量的最佳实践。 亚马逊云科技开发者社区为开发者们提供全球的…

SD三分钟入门!秋叶大佬24年8月最新的Stable Diffusion整合包V4.9.7来了~

先感谢赛博菩萨秋葉大佬&#xff0c;开发绘世启动器&#xff0c;**8月15日更新了秋叶整合包最新版本4.9。**文末有安装包&#xff01;&#xff01; SD整合包可以扫描下方,免费获取 1 什么是 Stable Diffusion&#xff1f; Stable Diffusion&#xff08;简称SD&#xff09;是…

一键编译QT5源码脚本(交叉编译arm64、mips64版本)

前言 这几天为了编写国产专用机上的软件&#xff0c;又盘起了交叉编译.. 一开始想使用深度最新的deepin 23正式版做系统&#xff0c;搭建编译环境。然而交叉编译链工具直接安装失败&#xff01; 然后又装了Debian12原版系统&#xff0c;编译环境倒是顺利搭建起来&#xff0c…

DDIA 分布式数据的分区与复制 - 基于 Redis、Kafka、Elasticsearch 的深入分析

引言 本文基于《Designing Data-Intensive Applications》一书&#xff08;设计数据密集型应用&#xff0c;简称 DDIA&#xff09;&#xff0c;深入探讨了 Redis、Kafka 和 Elasticsearch 等常用组件的分区与复制机制。通过这些案例分析&#xff0c;我们可以更好地理解分布式系…

Java Web实战教程:如何一步步开发美容美发管理系统

✍✍计算机毕业编程指导师 ⭐⭐个人介绍&#xff1a;自己非常喜欢研究技术问题&#xff01;专业做Java、Python、微信小程序、安卓、大数据、爬虫、Golang、大屏等实战项目。 ⛽⛽实战项目&#xff1a;有源码或者技术上的问题欢迎在评论区一起讨论交流&#xff01; ⚡⚡ Java、…

Python编码系列—Docker容器的高效使用与实战应用

&#x1f31f;&#x1f31f; 欢迎来到我的技术小筑&#xff0c;一个专为技术探索者打造的交流空间。在这里&#xff0c;我们不仅分享代码的智慧&#xff0c;还探讨技术的深度与广度。无论您是资深开发者还是技术新手&#xff0c;这里都有一片属于您的天空。让我们在知识的海洋中…

Linux系统(Centos7)没有安装GUI图形界面后期加装方法

问题背景 前期图方便安装了centos7的命令行版本&#xff0c;后期发现需要有图形界面才行&#xff0c;所以需要在后期加装图形界面。 问题解决 必要要求&#xff1a;服务器能够连接互联网&#xff0c;如果是VMware,网络选择NAT&#xff0c;开机后就可以联网&#xff1b;所有操…

《上海包装》是什么级别的期刊?是正规期刊吗?能评职称吗?

​问题解答 问&#xff1a;《上海包装》是不是核心期刊&#xff1f; 答&#xff1a;不是&#xff0c;是知网收录的正规学术期刊。 问&#xff1a;《上海包装》级别&#xff1f; 答&#xff1a;省级。主管单位&#xff1a;上海世纪出版&#xff08;集团&#xff09;有限公司…

noge-gyp构建项目踩坑记录

开发环境 系统: win11 node: 19.7.0 npm: 8.3.2 node-gyp: 10.0.2可以不使用windows-build-tools来安装构建工具,手动进行安装 我这边用windows-build-tools安装时候会提示 process.env only accepts a configurable, writable, and enumerable data descriptor. 查了资料后…

Autosar工程师必读:Vector工具链自动化实战指南<一>

----自动化不仅是一种技术&#xff0c;更是一种思维方式&#xff0c;它将帮助我们在快节奏的工作环境中保持领先&#xff01; 目录 往期推荐 场景1&#xff1a;代码生成 用法示例 参数说明 场景2&#xff1a;项目更新 用法示例 参数说明 场景3&#xff1a;导出Arxml 用…

【设计模式之原型模式——矩形原型】

原型模式的基本实现 创建⼀个抽象类或接⼝&#xff0c;声明⼀个克隆⽅法 clone 具体原型类去实现接口&#xff0c;重写克隆⽅法 客户端中实例化具体原型类的对象&#xff0c;并调⽤其克隆⽅法来&#xff08;赋给&#xff09;创建新的对象。 什么时候实现原型模式 &#xff1f;…

游戏开发设计模式之模板方法模式

目录 模板方法模式在游戏开发中的具体应用案例是什么&#xff1f; 如何在不同类型的游戏&#xff08;如角色扮演游戏、策略游戏等&#xff09;中实现模板方法模式&#xff1f; 模板方法模式与其他设计模式&#xff08;如观察者模式、状态模式等&#xff09;相比&#xff0c;…

【C语言篇】

C语言是一种广泛使用的计算机编程语言&#xff0c;它以其高效、灵活和功能强大而著称。以下是一些C语言中的常见知识点&#xff1a; 基本语法&#xff1a; 变量声明与初始化 数据类型&#xff08;整型、浮点型、字符型等&#xff09; 控制语句&#xff08;if、for、while、do…

分布式场景下websocket解决方案

在项目中遇到&#xff1a;多个服务作为websocket服务端时&#xff0c;怎么跟前端设备进行数据通信的问题。具体解决方案&#xff0c;分享一下。 1.遇到问题 项目中使用websocket与前端设备建立长链接&#xff0c;用于推送过车、车位数、支付等相关信息&#xff0c;由于项目是负…