# 神奇小事杂记

## 小众命令：getent

### getent 是什么

> ```makefile
> get entries from Name Service Switch libraries
> ```

根据我的观察，身边共事过的同事，都没用过、甚至没听过getent

### 与getent的偶遇

这要回到 2022 年了，当时作为刷推爱好者，偶然刷到了以下推文

> 在没有 ping/dig/nslookup 的时候，可以使用 getent 命令解析域名。 `getent hosts`[`http://google.com`](http://google.com%60)

第一眼就觉得很神奇，惊呼，还能这样玩？果断点赞+收藏。推特果然是一个学习技术的好地方。更神奇的是一周后，我在排查 k8s 环境中的一个问题时，需要在一个业务 pod 中进行域名解析，但是当时运维团队可能是出于安全原因，不允许直接在 pod 中安装第三方软件，当时也就灵光一现，马上用到了 getent，简单、小众、好用。最重要的是`getent`是一个标准的 GNU 工具, 因此几乎所有的 Linux 发行版都包含了它，非常值得收藏。

最近同事有类似域名解析的需求，果断推荐了一把 getent ，它值得更广泛的传播度。

## 如何获取 zk 角色

一些前置背景：

笔者所在的团队主要项目就是做一个云原生大数据运维管控平台，通俗来说就是将大数据组件诸如：zk、kafka 等部署在 k8s 上、hdfs 则在主机上以容器化方式部署。

笔者日常review代码的过程中，发现一个有意思的地方，在 k8s 中部署 zk 集群，每个 zk 节点都要暴露 nodeport，有一个需求是获取这个 zk 集群中每个节点的角色，历史做法是进入到这个 zk 的 pod 中，并执行以下命令

```bash
# zkServer.sh status
Mode: follower
```

来看看具体耗时

```bash
time kubectl -n enginemanager-w70f exec -it pod-zknode-9809-42051  bin/zkServer.sh status
kubectl exec [POD] [COMMAND] is DEPRECATED and will be removed in a future version. Use kubectl exec [POD] -- [COMMAND] instead.
ZooKeeper JMX enabled by default
Using config: /opt/zookeeper/bin/../conf/zoo.cfg
Client port found: 2181. Client address: localhost. Client SSL: false.
Mode: follower

real    0m0.324s
user    0m0.066s
sys     0m0.028s
```

笔者天然觉得这种做法不够友好了，秉承着相信一定有更好的解决办法的信念，开启搜索大法，果真找一个更高效的做法：

```bash
# time echo stat | nc 172.18.5.30 32507 | grep Mode
Mode: follower

real    0m0.013s
user    0m0.009s
sys     0m0.006s
```

0.324s 与 0.013s，25 倍的差距，不可谓不惊人，也是没想到 nc 还可以这么用。

## 如何获取 hdfs 的 active namenode

与 zk 的不同之处在于，hdfs是以容器化的方式部署在主机上，而非部署在 k8s 中，获取 active的 namenode 方式则是进入 namenode 容器中执行命令获取

```bash
# time docker exec -it 1b5d208efc1e /opt/hadoop/bin/hdfs haadmin -getServiceState nn42168
……
active

real    0m1.096s
user    0m0.022s
sys     0m0.011s
```

耗时1s多，还是挺费时间的，通过笔者的调研，发现更高效的办法：使用 hdfs 的 jmx 接口，如下所示：

```bash
# curl   -s -w 'Total: %{time_total}s\n'  http://172.18.5.155:50070/jmx?qry=Hadoop:service=NameNode,name=NameNodeStatus
{
  "beans" : [ {
    "name" : "Hadoop:service=NameNode,name=NameNodeStatus",
    "modelerType" : "org.apache.hadoop.hdfs.server.namenode.NameNode",
    "NNRole" : "NameNode",
    "HostAndPort" : "hadoop-4zd6-501:8020",
    "SecurityEnabled" : false,
    "LastHATransitionTime" : 1709638327400,
    "BytesWithFutureGenerationStamps" : 0,
    "SlowPeersReport" : null,
    "SlowDisksReport" : null,
    "State" : "active"
  } ]
}Total: 0.002s
```

才 0.002s 而已，也就是 1s 的 1/500，可怕的差距。

## 总结

getent 属于一个经验之道，知道就是知道，不知道也会想到其它方法，只是可能没有 getent 那么称手而已；zk 与 hdfs 的优化，更多的是一种偏执的信念，对于不友好实现的敏感，以及对于高效的孜孜不倦的追求。

---

[参考](https://t.co/ZKvswgk4eW)

* [http](https://t.co/ZKvswgk4eW)[s://twitter.com/0x80i/status/1521392601731002368](https://twitter.com/0x80i/status/1521392601731002368)
    
* [https://man7.org/linux/man-pages/man1/getent.1.html](https://man7.org/linux/man-pages/man1/getent.1.html)
    
* [https://stackoverflow.com/questions/48924122/how-to-check-which-zookeeper-instance-is-the-leader-within-an-ensemble](https://stackoverflow.com/questions/48924122/how-to-check-which-zookeeper-instance-is-the-leader-within-an-ensemble)
