这个是github上官方文档如果向安装kurbernets就看readme.md
readme.md最好使用microsoft visual studio打开
右边这个书籍按钮,按一下就会出现上面图片的右边,更容易理解。
使用windows10安装完dockerdesktop后,如果你是刚开始学习容器化的docker,你首先使用docker run -d -p 80:80 docker/getting-started
然后进入
放在方面会出现open in brower选项将docker的实例做一遍,要不然后面的命令你可能不会了解。
这些完成后安装k8s的必要部件后:我直接给源码把:
springboot:
springboot的启动类DemoApplication:
package com.example.demo;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
@SpringBootApplication
public class DemoApplication {
public static void main(String[] args) {
SpringApplication.run(DemoApplication.class,args);
}
}
application.properties
server.port=81 #这个要和deployment.yaml的containerport一致否则会出现无法连接到service的情况
spring.jpa.database=MYSQL
spring.datasource.url=jdbc:mysql://mysql-service:3306/tdBackupServer?useUnicode=true&characterEncoding=utf8&useSSL=false&useLegacyDatetimeCode=false&serverTimezone=UTC&createDatabaseIfNotExist=true
#createDatabaseIfNotExist=true有这个参数就算你的mysql没有数据库tdBackupServer也会自动创立
spring.datasource.driverClassName=com.mysql.jdbc.Driver
spring.jpa.show-sql=true
spring.datasource.username=root
spring.datasource.password=123456
spring.datasource.schema=classpath:schema.sql
spring.datasource.initialization-mode=always
#这些都是springboot的基础
controller类:
package com.example.demo.controller;
import com.example.demo.entity.Person;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
import java.util.Map;
@RestController //controller里面的方法都以json格式输出,不用再写什么jackjson配置的了
public class TestController {
// @Autowired
// AddPersonS addPersonS;
@Autowired
JdbcTemplate jdbcTemplate;
@RequestMapping("/getNumber") //RequestMapping是通过将用户对地址的getNumber请求使用getNuber方法来回应
public String getNumber() {
return "简单的SpringBoot,你出来了";
}
@ResponseBody
@RequestMapping("/add")
public List
后面的server类,dao类,entity类可以不需要因为我直接在controller就使用JdbcTemplate jdbcTemplate对数据库进行操作。完整的springboot可不止这些。
与application相同resource下的schema.sql是用来对springboot创建tdBackupServer后对数据表进行创建的;
SET FOREIGN_KEY_CHECKS=0;
DROP TABLE IF EXISTS `person`;
CREATE TABLE `person` (
`id` int(11) NOT NULL ,
`name` varchar(255) DEFAULT ''
) DEFAULT CHARSET=utf8;
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0modelVersion>
<parent>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-parentartifactId>
<version>2.3.6.RELEASEversion>
<relativePath/>
parent>
<groupId>com.examplegroupId>
<artifactId>demoartifactId>
<version>0.0.1-SNAPSHOTversion>
<name>demoname>
<description>Demo project for Spring Bootdescription>
<properties>
<java.version>1.8java.version>
properties>
<dependencies>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-webartifactId>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starterartifactId>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-loggingartifactId>
<version>2.0.1.RELEASEversion>
<scope>compilescope>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-testartifactId>
<scope>testscope>
<exclusions>
<exclusion>
<groupId>org.junit.vintagegroupId>
<artifactId>junit-vintage-engineartifactId>
exclusion>
exclusions>
dependency>
<dependency>
<groupId>org.mybatis.spring.bootgroupId>
<artifactId>mybatis-spring-boot-starterartifactId>
<version>1.1.1version>
dependency>
<dependency>
<groupId>mysqlgroupId>
<artifactId>mysql-connector-javaartifactId>
<version>5.1.40version>
dependency>
<dependency>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-starter-jdbcartifactId>
dependency>
<dependency>
<groupId>junitgroupId>
<artifactId>junitartifactId>
<scope>testscope>
dependency>
<dependency>
<groupId>org.springframeworkgroupId>
<artifactId>spring-testartifactId>
<version>RELEASEversion>
<scope>compilescope>
dependency>
dependencies>
<build>
<plugins>
<plugin>
<groupId>org.springframework.bootgroupId>
<artifactId>spring-boot-maven-pluginartifactId>
plugin>
plugins>
build>
project>
然后就是使用springboot自带的服务器的设置:
MainClass是springboot的启动类DemoApplication的地址:
mysql的密码是123456,端口是默认的3306,用户为root;
然后我们在IDEA的项目目录下执行:mvn package
默认情况下会打包到D:\IDEA\demo\target 下:文件名是默认生成的demo-0.0.1-SNAPSHOT.jar,这是一个可执行的jar包
在当前目录下创建Dockerfile文件:因为使用
docker build -t tdbackup:lastest . 代表将当前目录的dockerfile文件进行镜像构建,而且ADD,COPY只能通过相对目录,如果里面的ADD,COPY是绝对路径很可能出现找不到文件的情况。
里面写着:
FROM java:8-jdk-alpine #
WORKDIR /app
ADD ./demo-0.0.1-SNAPSHOT.jar /app/app.jar
#EXPOSE 8080 这个如果和jar包的server.prot不同,默认会使用jar包的server.port而忽视expose
ENTRYPOINT [ "java","-jar","app.jar" ]
然后再命令行执行:
docker build -t tdbackup:lastest .
然后dockerdesktop会出现一个镜像
之后我们的springboot项目就成了tdbackup镜像:
然后创建多个yaml文件:
这四个文件内容:
deployment.yaml:
apiVersion: apps/v1
kind: Deployment
metadata:
name: tdbackdeploment
labels:
app: tdbackdeploment
spec:
replicas: 3
selector:
matchLabels:
app: tdbackcontainer
template:
metadata:
labels:
app: tdbackcontainer
spec:
containers:
- name: tdbackcontainer
image: tdbackup:lastest
imagePullPolicy: IfNotPresent
ports:
- containerPort: 81
apiVersion: v1
kind: Service
metadata:
name: tdservice
namespace: default
labels:
app: tdservice
spec:
type: NodePort
ports:
- protocol: TCP
port: 81 #这里的端口和clusterIP对应,即ip:8080,供内部访问
targetPort: 81 #端口一定要和container暴露出来的端口对应
nodePort: 30090 #默认是30000-32767 所有的只有type=node节点都会开放此端口,此端口供外部调用。
selector: #选择label 只支持基于相等性的条件 不是根据名字来选择nodeport的 app=tdbackdeploment, app in(tdbackdeploment)都是相同的
app: tdbackcontainer
#NodePorts,LoadBalancers是放在Kubernete外部的(比如我们有单独的物理机来承担数据库的角色),NodePort:使用一个集群固定IP,但是额外在每个POD上均暴露这个服务,端口
#Replication Controller只会对那些RestartPolicy = Always的Pod的生效,其他无视
#sessionAffinity: None
apiVersion: v1
kind: Endpoints #这个服务具有IP+port,可以自己设定,连接的外部服务器地址
metadata:
name: mysql-service # 这个mysql.yaml根据名字而非labels将endpoint和ip地址连接
namespace: default
labels:
app: mysql-service
subsets:
- addresses: #Endpoints的subsets中指定了需要连接的外部服务器的IP和端口
- ip: 192.168.1.81 #这个是我的主机的ip地址
ports:
- port: 3306
#url: jdbc:mysql:// mysql-endpoints:3306/tdBackupServer?useUnicode=true&characterEncoding=utf8&useSSL=false&useLegacyDatetimeCode=false&serverTimezone=UTC&createDatabaseIfNotExist=true
#endpoints是服务使用selector 选择器 选择pods后自动创建的,所有对于mysql-sevrice服务的请求都会转到ip:192.168.1.81:3306里面去
apiVersion: v1
kind: Service
metadata:
name: mysql-service #service和配套的endpoints必须相同,因为使用selector就是对有相应的label的pods或者外部的mysql映射地址
#使用selector会自动创建一个与service相同名字的endpoints,如果需要自己配置那么endpoints的名字也必须和service一致
#这样才能自动绑定service和endpoints
namespace: default
spec:
ports:
- port: 3306
selector:
app: mysql-service #service与对应的endpoints(自己声明的),如果name不一致就算label一致也无法自动绑定,但是如果name一致就算不用selector也可以绑定,selector本来就是
#自动创建一个name相同的endpoint达到
然后就是激动人心的部署阶段:
命令行模式到达你的这些yaml文件的目录下,也可以使用
windows power shell
然后执行`
kubectl apply -f endpoint.yaml
kubectl apply -f mysql.yaml
kubectl apply -f deployment.yaml
kubectl apply -f service.yaml
发现tdservice和mysql-service这两个service没有绑定对应的endpoints,一定出错了
结果是我的deployment.yaml文件名错误,是deploment.yaml
mysql-service没有和我们的endpoint绑定起来,如果service的endpoint没有地址那么就是没有绑定endpoints。
我发现一个奇怪的问题:我的分布式k8s中有ubunto的pods当我把ubunto容器全部关闭的时候我的mysql-service才和endpoints绑定起来,
出现容器无法启动的情况,使用describe查看pods详细信息,发现最一行:
failed to pull image "tdbackup:lastest": rpc error: code = Unknown desc = Error response from daemon: pull access denied for tdbackup, repository does not exist or may require 'docker login': denied: requested access to the resource is denied
原因:事先没有使用docker login登录所以没有权限拉取镜像。
确定自己的mysql有远程访问的权限:
通过:
user mysql;
select host,user from user;
查看是否含有远程连接权限,
如果是下图有 % root (代表远程任意ip可以通过root用户连接数据库)
修改操作为:
update user set host = '%' where user = 'root';
flush privileges;
到这步就可以在主机使用localhost:30090就可一访问界面了。
第一次连接我是成功的,但是等我全部删除掉配置文件重新载入就这一步我出新问题了,QWQ.
我的问题是:无论我怎么测试mysql的连接,我就是出现connection
refused错误:
然后我的最后解决方法:我又创建了一个mysql的pods使用deployment管理,使用service将pods ip和service.name绑定在一起,我的kube-dns默认是打开的,最后改一下springboot的url
:
spring.datasource.url=jdbc:mysql://test-service:3307/tdBackupServer?useUnicode=true&characterEncoding=utf8&useSSL=false&useLegacyDatetimeCode=false&serverTimezone=UTC&createDatabaseIfNotExist=true
#test-service是mysql pods的service
test-mysql.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: mysql-test
labels:
app: mysql-test
spec:
replicas: 1
selector:
matchLabels:
app: mysql-test-container
template:
metadata:
labels:
app: mysql-test-container
spec:
containers:
- name: mysql-test-container
image: mysql:5.7
imagePullPolicy: IfNotPresent
env:
- name : MYSQL_ROOT_PASSWORD
value : '123456'
test-mysql-service.yaml
apiVersion: v1
kind: Service
metadata:
name: test-service
labels:
app: test-service
spec:
selector:
app: mysql-test-container
ports:
- port: 3307
targetPort: 3306
最后我成功了,但是为什么我的主机作为一个独立的endpoint绑定到service却无法使用。。
其中只有一个pods在我使用浏览器访问项目时会执行我的/ADD对数据库进行操作。