Linux 上 httpdns client 实现实战

最近在执行devops 时,采用了容器云平台,性能很好,非常便捷,但是
通过互联网访问时,偶尔遇到域名解析不了,但是一会儿又好了。
通过各种方式排查问题,排除了bind-dns 故障和mesos-dns 故障,
发现在集群之外的公网,域名故障才是问题,集群之内的11台虚拟机一切运转正常。
这到底是什么原因引起的呢?

这是传统的DNS UDP 53 端口 机制导致的, DNS 通过公网服务器,会缓存记录,
使用httpdns 可以避免域名被劫持,提高域名的可访问性。

但是只听过httpdns 用于 移动app上,还没看到谁在linux 平台上使用httpdns 客户端。 也没现成的代码可以参考。

摸清楚httpdns 原理后,
查询了mesos-dns 确实又提供httpdns 接口,默认端口8123,
happy:Downloads happy$ curl http://10.2.1.71:8123/v1/hosts/jenkins.devops.marathon.mesos
[
{
“host”: “jenkins.devops.marathon.mesos.”,
“ip”: “172.30.102.15”
}
于是一个大胆的想法来了。
直接把httpdns 内容更新后写入本地hosts 文件,不就OK了吗?

在这里插入图片描述

于是写了个httpdns.sh 脚本,使用 root用户执行,
https://github.com/HappyFreeAngel/httpdns-client

详细代码如下:

#!/bin/bash

export MARATHON_HTTP_PORT=8080
export MARATHON_HOST_LIST="10.2.1.71,10.2.1.72,10.2.1.73"

#确保shell 切换到当前shell 脚本文件夹
current_file_path=$(cd "$(dirname "$0")"; pwd)
cd ${current_file_path}

while true
do
    date
    echo "判断marathon leader"
    for marathon_host in $(echo $MARATHON_HOST_LIST | tr ',' "\n")
         do
            leader_query_result=$(curl --silent http://${marathon_host}:8080/v2/leader | grep '\"leader\":' | tr '\"' ' ' | tr ':' ' ' | awk '{ print $3}')
            if [[ ! -z "$leader_query_result" ]];
            then
                MARATHON_LEADER=$leader_query_result
                break
            fi
         done
    #get marathon leader
    #http://10.20.5.71:8080/v2/leader
    #{"leader":"10.20.5.72:8080"}
    if [[ -z "$MARATHON_LEADER" ]];
    then
         echo "ERROR! Marathon Leader is unknown!"     #todo 如果是单个marathon 会不会报错?
         exit 1
    fi

    app_id_list=$(curl --silent http://${MARATHON_LEADER}:8080/v2/apps/ | jq '.apps' | jq [.[].id] | tr '[' " " | tr ']' " " | tr '\"' " " | tr '\,' " ")

    touch temp_hosts.txt

    `rm -f temp_hosts_latest.txt`
    touch temp_hosts_latest.txt

    for app_id in $app_id_list
        do
            arr=(`echo $app_id | tr '/' ' '`)
            count=${#arr[@]}
            app_domain=""
            for(( i=count-1;i>=0;i--))
            {
               if [[ -z $app_domain ]];
               then
                   app_domain=${arr[i]}
               else
                  app_domain="${app_domain}.${arr[i]}"
               fi
            }
            app_domain="${app_domain}.marathon.mesos"
            #row_host_record=$(curl http://10.2.1.71:8123/v1/hosts/jenkins.devops.marathon.mesos | jq .[] | jq  '(.ip +" "+ .host)')
            ip=$(curl --silent http://${MARATHON_LEADER}:8123/v1/hosts/${app_domain} | jq .[] | jq  '.ip' | tr '"' " ")
            if [[ ! -z "$ip" ]];
            then
                row_host_record="${ip}  ${app_domain}"
                echo $row_host_record >> temp_hosts_latest.txt
            fi
       done

       #判断过去的时间里是否有变化。
       old_hosts_md5_value=$(md5 temp_hosts.txt | awk '{print $4}')
       latest_hosts_md5_value=$(md5 temp_hosts_latest.txt | awk '{print $4}')

       if [[ $latest_hosts_md5_value != $old_hosts_md5_value ]];
       then
             cp hosts.j2  /etc/hosts
             cat temp_hosts_latest.txt >> /etc/hosts

             #显示一下差异
              diff_result=$(diff temp_hosts.txt  temp_hosts_latest.txt)
              date >> ${current_file_path}/domain_change_history.log
              echo $diff_result >> ${current_file_path}/domain_change_history.log
              echo $diff_result

             `rm -f temp_hosts.txt`
             mv temp_hosts_latest.txt temp_hosts.txt
             echo "记录已经发生变化,主动更新了本地hosts记录."
             date
       else
           echo "休息30秒,再继续检测"
           sleep 30
       fi
done

在这里插入图片描述

在这里插入图片描述
在这里插入图片描述

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

开心自由天使

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值