Nexus Kubernetes クラスターの監視
各 Nexus Kubernetes クラスターは、複数のレイヤーで構成されます。
- 仮想マシン (VM)
- Kubernetes レイヤー
- アプリケーション ポッド
図: Nexus Kubernetes クラスターのサンプル
インスタンスでは、Nexus Kubernetes クラスターは、オプションの Container Insights 監視ソリューションと共に提供されます。 Container Insights では、Nexus Kubernetes クラスターとワークロードからログとメトリックをキャプチャします。 このツールを有効にするか、独自のテレメトリ スタックをデプロイするかは、お客様の判断です。
Azure 監視ツールを使用した Nexus Kubernetes クラスターは次のようになります。
図: 監視ツールを使用した Nexus Kubernetes クラスター
マネージド ID 認証を使用した CLI での拡張機能のオンボード
Azure CLI 以降のドキュメントで、複数のオペレーティング システムにインストールする方法、および CLI 拡張機能をインストールする方法について説明します。
必要な CLI 拡張機能の最新バージョンをインストールします。
Nexus Kubernetes クラスターの監視 - VM レイヤー
このハウツー ガイドでは、Nexus Kubernetes クラスター仮想マシンを Azure に Arc 接続し、Azure Monitoring Agent を使用してこれらの VM からシステム ログを収集するための監視エージェントを有効にする手順とユーティリティ スクリプトについて説明します。 この手順では、Log Analytics ワークスペースにログ データ収集を設定する方法について詳しく説明します。
サポートを提供するリソースを次に示します。
arc-connect.env
: このテンプレート ファイルを使用して、含まれているスクリプトに必要な環境変数を作成します
export SUBSCRIPTION_ID=""
export SERVICE_PRINCIPAL_ID=""
export SERVICE_PRINCIPAL_SECRET=""
export RESOURCE_GROUP=""
export TENANT_ID=""
export LOCATION=""
export INSTALL_AZURE_MONITOR_AGENT="true"
export PROXY_URL=""
export NAMESPACE=""
export AZURE_MONITOR_AGENT_VERSION="1.24.2"
export CONNECTEDMACHINE_AZCLI_VERSION="0.6.0"
dcr.sh
: このスクリプトを使用して、Syslog コレクションを構成するデータ収集規則 (DCR) を作成します
#!/bin/bash
set -e
SUBSCRIPTION_ID="${SUBSCRIPTION_ID:?SUBSCRIPTION_ID must be set}"
SERVICE_PRINCIPAL_ID="${SERVICE_PRINCIPAL_ID:?SERVICE_PRINCIPAL_ID must be set}"
SERVICE_PRINCIPAL_SECRET="${SERVICE_PRINCIPAL_SECRET:?SERVICE_PRINCIPAL_SECRET must be set}"
RESOURCE_GROUP="${RESOURCE_GROUP:?RESOURCE_GROUP must be set}"
TENANT_ID="${TENANT_ID:?TENANT_ID must be set}"
LOCATION="${LOCATION:?LOCATION must be set}"
LAW_RESOURCE_ID="${LAW_RESOURCE_ID:?LAW_RESOURCE_ID must be set}"
DCR_NAME=${DCR_NAME:-${RESOURCE_GROUP}-syslog-dcr}
az login --service-principal -u "${SERVICE_PRINCIPAL_ID}" -p "${SERVICE_PRINCIPAL_SECRET}" -t "${TENANT_ID}"
az account set -s "${SUBSCRIPTION_ID}"
az extension add --name monitor-control-service
RULEFILE=$(mktemp)
tee "${RULEFILE}" <<EOF
{
"location": "${LOCATION}",
"properties": {
"dataSources": {
"syslog": [
{
"name": "syslog",
"streams": [
"Microsoft-Syslog"
],
"facilityNames": [
"auth",
"authpriv",
"cron",
"daemon",
"mark",
"kern",
"local0",
"local1",
"local2",
"local3",
"local4",
"local5",
"local6",
"local7",
"lpr",
"mail",
"news",
"syslog",
"user",
"uucp"
],
"logLevels": [
"Info",
"Notice",
"Warning",
"Error",
"Critical",
"Alert",
"Emergency"
]
}
]
},
"destinations": {
"logAnalytics": [
{
"workspaceResourceId": "${LAW_RESOURCE_ID}",
"name": "centralWorkspace"
}
]
},
"dataFlows": [
{
"streams": [
"Microsoft-Syslog"
],
"destinations": [
"centralWorkspace"
]
}
]
}
}
EOF
az monitor data-collection rule create --name "${DCR_NAME}" --resource-group "${RESOURCE_GROUP}" --location "${LOCATION}" --rule-file "${RULEFILE}" -o tsv --query id
rm -rf "${RULEFILE}"
assign.sh
: このスクリプトを使用して、DCR をリソース グループ内のすべての Arc 対応サーバーに関連付けるポリシーを作成します
#!/bin/bash
set -e
SUBSCRIPTION_ID="${SUBSCRIPTION_ID:?SUBSCRIPTION_ID must be set}"
SERVICE_PRINCIPAL_ID="${SERVICE_PRINCIPAL_ID:?SERVICE_PRINCIPAL_ID must be set}"
SERVICE_PRINCIPAL_SECRET="${SERVICE_PRINCIPAL_SECRET:?SERVICE_PRINCIPAL_SECRET must be set}"
RESOURCE_GROUP="${RESOURCE_GROUP:?RESOURCE_GROUP must be set}"
TENANT_ID="${TENANT_ID:?TENANT_ID must be set}"
LOCATION="${LOCATION:?LOCATION must be set}"
DCR_NAME=${DCR_NAME:-${RESOURCE_GROUP}-syslog-dcr}
POLICY_NAME=${POLICY_NAME:-${DCR_NAME}-policy}
az login --service-principal -u "${SERVICE_PRINCIPAL_ID}" -p "${SERVICE_PRINCIPAL_SECRET}" -t "${TENANT_ID}"
az account set -s "${SUBSCRIPTION_ID}"
DCR=$(az monitor data-collection rule show --name "${DCR_NAME}" --resource-group "${RESOURCE_GROUP}" -o tsv --query id)
PRINCIPAL=$(az policy assignment create \
--name "${POLICY_NAME}" \
--display-name "${POLICY_NAME}" \
--resource-group "${RESOURCE_GROUP}" \
--location "${LOCATION}" \
--policy "d5c37ce1-5f52-4523-b949-f19bf945b73a" \
--assign-identity \
-p "{\"dcrResourceId\":{\"value\":\"${DCR}\"}}" \
-o tsv --query identity.principalId)
required_roles=$(az policy definition show -n "d5c37ce1-5f52-4523-b949-f19bf945b73a" --query policyRule.then.details.roleDefinitionIds -o tsv)
for roleId in $(echo "$required_roles"); do
az role assignment create \
--role "${roleId##*/}" \
--assignee-object-id "${PRINCIPAL}" \
--assignee-principal-type "ServicePrincipal" \
--scope /subscriptions/"$SUBSCRIPTION_ID"/resourceGroups/"$RESOURCE_GROUP"
done
install.sh
: 各 VM に Azure Monitor エージェントをインストールして、Azure Virtual Machines から監視データを収集します。
#!/bin/bash
set -e
function create_secret() {
kubectl apply -f - -n "${NAMESPACE}" <<EOF
apiVersion: v1
kind: Secret
metadata:
name: naks-vm-telemetry
type: Opaque
stringData:
SUBSCRIPTION_ID: "${SUBSCRIPTION_ID}"
SERVICE_PRINCIPAL_ID: "${SERVICE_PRINCIPAL_ID}"
SERVICE_PRINCIPAL_SECRET: "${SERVICE_PRINCIPAL_SECRET}"
RESOURCE_GROUP: "${RESOURCE_GROUP}"
TENANT_ID: "${TENANT_ID}"
LOCATION: "${LOCATION}"
PROXY_URL: "${PROXY_URL}"
INSTALL_AZURE_MONITOR_AGENT: "${INSTALL_AZURE_MONITOR_AGENT}"
VERSION: "${AZURE_MONITOR_AGENT_VERSION}"
CONNECTEDMACHINE_AZCLI_VERSION: "${CONNECTEDMACHINE_AZCLI_VERSION}"
EOF
}
function create_daemonset() {
kubectl apply -f - -n "${NAMESPACE}" <<EOF
apiVersion: apps/v1
kind: DaemonSet
metadata:
name: naks-vm-telemetry
labels:
k8s-app: naks-vm-telemetry
spec:
selector:
matchLabels:
name: naks-vm-telemetry
template:
metadata:
labels:
name: naks-vm-telemetry
spec:
hostNetwork: true
hostPID: true
containers:
- name: naks-vm-telemetry
image: mcr.microsoft.com/oss/mirror/docker.io/library/ubuntu:20.04
env:
- name: SUBSCRIPTION_ID
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: SUBSCRIPTION_ID
- name: SERVICE_PRINCIPAL_ID
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: SERVICE_PRINCIPAL_ID
- name: SERVICE_PRINCIPAL_SECRET
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: SERVICE_PRINCIPAL_SECRET
- name: RESOURCE_GROUP
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: RESOURCE_GROUP
- name: TENANT_ID
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: TENANT_ID
- name: LOCATION
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: LOCATION
- name: PROXY_URL
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: PROXY_URL
- name: INSTALL_AZURE_MONITOR_AGENT
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: INSTALL_AZURE_MONITOR_AGENT
- name: VERSION
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: VERSION
- name: CONNECTEDMACHINE_AZCLI_VERSION
valueFrom:
secretKeyRef:
name: naks-vm-telemetry
key: CONNECTEDMACHINE_AZCLI_VERSION
securityContext:
privileged: true
command:
- /bin/bash
- -c
- |
set -e
WORKDIR=\$(nsenter -t1 -m -u -n -i mktemp -d)
trap 'nsenter -t1 -m -u -n -i rm -rf "\${WORKDIR}"; echo "Azure Monitor Configuration Failed"' ERR
nsenter -t1 -m -u -n -i mkdir -p "\${WORKDIR}"/telemetry
nsenter -t1 -m -u -n -i tee "\${WORKDIR}"/telemetry/telemetry_common.py > /dev/null <<EOF
#!/usr/bin/python3
import json
import logging
import os
import socket
import subprocess
import sys
arc_config_file = "\${WORKDIR}/telemetry/arc-connect.json"
class AgentryResult:
CONNECTED = "Connected"
CREATING = "Creating"
DISCONNECTED = "Disconnected"
FAILED = "Failed"
SUCCEEDED = "Succeeded"
class OnboardingMessage:
COMPLETED = "Onboarding completed"
STILL_CREATING = "Azure still creating"
STILL_TRYING = "Service still trying"
def get_logger(logger_name):
logger = logging.getLogger(logger_name)
logger.setLevel(logging.DEBUG)
handler = logging.StreamHandler(stream=sys.stdout)
format = logging.Formatter(fmt="%(name)s - %(levelname)s - %(message)s")
handler.setFormatter(format)
logger.addHandler(handler)
return logger
def az_cli_cm_ext_install(logger, config):
logger.info("Install az CLI connectedmachine extension")
proxy_url = config.get("PROXY_URL")
if proxy_url is not None:
os.environ["HTTP_PROXY"] = proxy_url
os.environ["HTTPS_PROXY"] = proxy_url
cm_azcli_version = config.get("CONNECTEDMACHINE_AZCLI_VERSION")
logger.info("Install az CLI connectedmachine extension: {cm_azcli_version}")
ext_cmd = f'/usr/bin/az extension add --name connectedmachine --version "{cm_azcli_version}" --yes'
run_cmd(logger, ext_cmd)
def get_cm_properties(logger, config):
hostname = socket.gethostname()
resource_group = config.get("RESOURCE_GROUP")
logger.info(f"Getting arc enrollment properties for {hostname}...")
az_login(logger, config)
property_cmd = f'/usr/bin/az connectedmachine show --machine-name "{hostname}" --resource-group "{resource_group}"'
try:
raw_property = run_cmd(logger, property_cmd)
cm_json = json.loads(raw_property.stdout)
provisioning_state = cm_json["provisioningState"]
status = cm_json["status"]
except:
logger.warning("Connectedmachine not yet present")
provisioning_state = "NOT_PROVISIONED"
status = "NOT_CONNECTED"
finally:
az_logout(logger)
logger.info(
f'Connected machine "{hostname}" provisioningState is "{provisioning_state}" and status is "{status}"'
)
return provisioning_state, status
def get_cm_extension_state(logger, config, extension_name):
resource_group = config.get("RESOURCE_GROUP")
hostname = socket.gethostname()
logger.info(f"Getting {extension_name} state for {hostname}...")
az_login(logger, config)
state_cmd = f'/usr/bin/az connectedmachine extension show --name "{extension_name}" --machine-name "{hostname}" --resource-group "{resource_group}"'
try:
raw_state = run_cmd(logger, state_cmd)
cme_json = json.loads(raw_state.stdout)
provisioning_state = cme_json["provisioningState"]
except:
logger.warning("Connectedmachine extension not yet present")
provisioning_state = "NOT_PROVISIONED"
finally:
az_logout(logger)
logger.info(
f'Connected machine "{hostname}" extenstion "{extension_name}" provisioningState is "{provisioning_state}"'
)
return provisioning_state
def run_cmd(logger, cmd, check_result=True, echo_output=True):
res = subprocess.run(
cmd,
shell=True,
stdout=subprocess.PIPE,
stderr=subprocess.PIPE,
universal_newlines=True,
)
if res.stdout:
if echo_output:
logger.info(f"[OUT] {res.stdout}")
if res.stderr:
if echo_output:
logger.info(f"[ERR] {res.stderr}")
if check_result:
res.check_returncode()
return res # can parse out res.stdout and res.returncode
def az_login(logger, config):
logger.info("Login to Azure account...")
proxy_url = config.get("PROXY_URL")
if proxy_url is not None:
os.environ["HTTP_PROXY"] = proxy_url
os.environ["HTTPS_PROXY"] = proxy_url
service_principal_id = config.get("SERVICE_PRINCIPAL_ID")
service_principal_secret = config.get("SERVICE_PRINCIPAL_SECRET")
tenant_id = config.get("TENANT_ID")
subscription_id = config.get("SUBSCRIPTION_ID")
cmd = f'/usr/bin/az login --service-principal --username "{service_principal_id}" --password "{service_principal_secret}" --tenant "{tenant_id}"'
run_cmd(logger, cmd)
logger.info(f"Set Subscription...{subscription_id}")
set_sub = f'/usr/bin/az account set --subscription "{subscription_id}"'
run_cmd(logger, set_sub)
def az_logout(logger):
logger.info("Logout of Azure account...")
run_cmd(logger, "/usr/bin/az logout --verbose", check_result=False)
EOF
nsenter -t1 -m -u -n -i tee "\${WORKDIR}"/telemetry/setup_azure_monitor_agent.py > /dev/null <<EOF
#!/usr/bin/python3
import json
import os
import socket
import time
import telemetry_common
def run_install(logger, ama_config):
logger.info("Install Azure Monitor agent...")
resource_group = ama_config.get("RESOURCE_GROUP")
location = ama_config.get("LOCATION")
proxy_url = ama_config.get("PROXY_URL")
hostname = socket.gethostname()
if proxy_url is not None:
os.environ["HTTP_PROXY"] = proxy_url
os.environ["HTTPS_PROXY"] = proxy_url
settings = (
'{"proxy":{"mode":"application","address":"'
+ proxy_url
+ '","auth": "false"}}'
)
cmd = f'/usr/bin/az connectedmachine extension create --no-wait --name "AzureMonitorLinuxAgent" --publisher "Microsoft.Azure.Monitor" --type "AzureMonitorLinuxAgent" --machine-name "{hostname}" --resource-group "{resource_group}" --location "{location}" --verbose --settings \'{settings}\''
else:
cmd = f'/usr/bin/az connectedmachine extension create --no-wait --name "AzureMonitorLinuxAgent" --publisher "Microsoft.Azure.Monitor" --type "AzureMonitorLinuxAgent" --machine-name "{hostname}" --resource-group "{resource_group}" --location "{location}" --verbose'
version = ama_config.get("VERSION")
if version is not None:
cmd += f' --type-handler-version "{version}"'
logger.info("Installing Azure Monitor agent...")
telemetry_common.az_login(logger, ama_config)
try:
telemetry_common.run_cmd(logger, cmd)
except:
logger.info("Trying to install Azure Monitor agent...")
finally:
telemetry_common.az_logout(logger)
def run_uninstall(logger, ama_config):
logger.info("Uninstall Azure Monitor agent...")
resource_group = ama_config.get("RESOURCE_GROUP")
hostname = socket.gethostname()
cmd = f'/usr/bin/az connectedmachine extension delete --name "AzureMonitorLinuxAgent" --machine-name "{hostname}" --resource-group "{resource_group}" --yes --verbose'
telemetry_common.az_login(logger, ama_config)
logger.info("Uninstalling Azure Monitor agent...")
try:
telemetry_common.run_cmd(logger, cmd)
except:
print("Trying to uninstall Azure Monitor agent...")
finally:
telemetry_common.az_logout(logger)
def ama_installation(logger, ama_config):
logger.info("Executing AMA extenstion installation...")
telemetry_common.az_cli_cm_ext_install(logger, ama_config)
# Get connected machine properties
cm_provisioning_state, cm_status = telemetry_common.get_cm_properties(
logger, ama_config
)
if (
cm_provisioning_state == telemetry_common.AgentryResult.SUCCEEDED
and cm_status == telemetry_common.AgentryResult.CONNECTED
):
# Get AzureMonitorLinuxAgent extension status
ext_provisioning_state = telemetry_common.get_cm_extension_state(
logger, ama_config, "AzureMonitorLinuxAgent"
)
if ext_provisioning_state == telemetry_common.AgentryResult.SUCCEEDED:
logger.info(telemetry_common.OnboardingMessage.COMPLETED)
return True
elif ext_provisioning_state == telemetry_common.AgentryResult.FAILED:
run_uninstall(logger, ama_config)
logger.warning(telemetry_common.OnboardingMessage.STILL_TRYING)
return False
elif ext_provisioning_state == telemetry_common.AgentryResult.CREATING:
logger.warning(telemetry_common.OnboardingMessage.STILL_CREATING)
return False
else:
run_install(logger, ama_config)
logger.warning(telemetry_common.OnboardingMessage.STILL_TRYING)
return False
else:
logger.error("Server not arc enrolled, enroll the server and retry")
return False
def main():
timeout = 60 # TODO: increase when executed via systemd unit
start_time = time.time()
end_time = start_time + timeout
config_file = telemetry_common.arc_config_file
logger = telemetry_common.get_logger(__name__)
logger.info("Running setup_azure_monitor_agent.py...")
if config_file is None:
raise Exception("config file is expected")
ama_config = {}
with open(config_file, "r") as file:
ama_config = json.load(file)
ama_installed = False
while time.time() < end_time:
logger.info("Installing AMA extension...")
try:
ama_installed = ama_installation(logger, ama_config)
except Exception as e:
logger.error(f"Could not install AMA extension: {e}")
if ama_installed:
break
logger.info("Sleeping 30s...") # retry for Azure info
time.sleep(30)
if __name__ == "__main__":
main()
EOF
nsenter -t1 -m -u -n -i tee "\${WORKDIR}"/arc-connect.sh > /dev/null <<EOF
#!/bin/bash
set -e
echo "{\"VERSION\": \"\${VERSION}\", \"SUBSCRIPTION_ID\": \"\${SUBSCRIPTION_ID}\", \"SERVICE_PRINCIPAL_ID\": \"\${SERVICE_PRINCIPAL_ID}\", \"SERVICE_PRINCIPAL_SECRET\": \"\${SERVICE_PRINCIPAL_SECRET}\", \"RESOURCE_GROUP\": \"\${RESOURCE_GROUP}\", \"TENANT_ID\": \"\${TENANT_ID}\", \"LOCATION\": \"\${LOCATION}\", \"PROXY_URL\": \"\${PROXY_URL}\", \"CONNECTEDMACHINE_AZCLI_VERSION\": \"\${CONNECTEDMACHINE_AZCLI_VERSION}\"}" > "\${WORKDIR}"/telemetry/arc-connect.json
if [ "\${INSTALL_AZURE_MONITOR_AGENT}" = "true" ]; then
echo "Installing Azure Monitor agent..."
/usr/bin/python3 "\${WORKDIR}"/telemetry/setup_azure_monitor_agent.py > "\${WORKDIR}"/setup_azure_monitor_agent.out
cat "\${WORKDIR}"/setup_azure_monitor_agent.out
if grep "Could not install AMA extension" "\${WORKDIR}"/setup_azure_monitor_agent.out > /dev/null; then
exit 1
fi
fi
EOF
nsenter -t1 -m -u -n -i sh "\${WORKDIR}"/arc-connect.sh
nsenter -t1 -m -u -n -i rm -rf "\${WORKDIR}"
echo "Server monitoring configured successfully"
tail -f /dev/null
livenessProbe:
initialDelaySeconds: 600
periodSeconds: 60
timeoutSeconds: 30
exec:
command:
- /bin/bash
- -c
- |
set -e
WORKDIR=\$(nsenter -t1 -m -u -n -i mktemp -d)
trap 'nsenter -t1 -m -u -n -i rm -rf "\${WORKDIR}"' ERR EXIT
nsenter -t1 -m -u -n -i tee "\${WORKDIR}"/liveness.sh > /dev/null <<EOF
#!/bin/bash
set -e
# Check AMA processes
ps -ef | grep "\\\s/opt/microsoft/azuremonitoragent/bin/agentlauncher\\\s"
ps -ef | grep "\\\s/opt/microsoft/azuremonitoragent/bin/mdsd\\\s"
ps -ef | grep "\\\s/opt/microsoft/azuremonitoragent/bin/amacoreagent\\\s"
# Check Arc server agent is Connected
AGENTSTATUS="\\\$(azcmagent show -j)"
if [[ \\\$(echo "\\\${AGENTSTATUS}" | jq -r .status) != "Connected" ]]; then
echo "azcmagent is not connected"
echo "\\\${AGENTSTATUS}"
exit 1
fi
# Verify dependent services are running
while IFS= read -r status; do
if [[ "\\\${status}" != "active" ]]; then
echo "one or more azcmagent services not active"
echo "\\\${AGENTSTATUS}"
exit 1
fi
done < <(jq -r '.services[] | (.status)' <<<\\\${AGENTSTATUS})
# Run connectivity tests
RESULT="\\\$(azcmagent check -j)"
while IFS= read -r reachable; do
if [[ ! \\\${reachable} ]]; then
echo "one or more connectivity tests failed"
echo "\\\${RESULT}"
exit 1
fi
done < <(jq -r '.[] | (.reachable)' <<<\\\${RESULT})
EOF
nsenter -t1 -m -u -n -i sh "\${WORKDIR}"/liveness.sh
nsenter -t1 -m -u -n -i rm -rf "\${WORKDIR}"
echo "Liveness check succeeded"
tolerations:
- operator: "Exists"
effect: "NoSchedule"
EOF
}
SUBSCRIPTION_ID="${SUBSCRIPTION_ID:?SUBSCRIPTION_ID must be set}"
SERVICE_PRINCIPAL_ID="${SERVICE_PRINCIPAL_ID:?SERVICE_PRINCIPAL_ID must be set}"
SERVICE_PRINCIPAL_SECRET="${SERVICE_PRINCIPAL_SECRET:?SERVICE_PRINCIPAL_SECRET must be set}"
RESOURCE_GROUP="${RESOURCE_GROUP:?RESOURCE_GROUP must be set}"
TENANT_ID="${TENANT_ID:?TENANT_ID must be set}"
LOCATION="${LOCATION:?LOCATION must be set}"
PROXY_URL="${PROXY_URL:?PROXY_URL must be set}"
INSTALL_AZURE_MONITOR_AGENT="${INSTALL_AZURE_MONITOR_AGENT:?INSTALL_AZURE_MONITOR_AGENT must be true/false}"
NAMESPACE="${NAMESPACE:?NAMESPACE must be set}"
AZURE_MONITOR_AGENT_VERSION="${AZURE_MONITOR_AGENT_VERSION:-"1.24.2"}"
CONNECTEDMACHINE_AZCLI_VERSION="${CONNECTEDMACHINE_AZCLI_VERSION:-"0.6.0"}"
create_secret
create_daemonset
前提条件 - VM
Nexus Kubernetes クラスターへのクラスター管理者アクセス。
Azure Arc 対応サーバーを使用するには、次の Azure リソース プロバイダーをサブスクリプションに登録します。
- Microsoft.HybridCompute
- Microsoft.GuestConfiguration
- Microsoft.HybridConnectivity
以前に次のリソース プロバイダーを登録していない場合は、登録します。
az account set --subscription "{the Subscription Name}"
az provider register --namespace 'Microsoft.HybridCompute'
az provider register --namespace 'Microsoft.GuestConfiguration'
az provider register --namespace 'Microsoft.HybridConnectivity'
- 必要に応じて、Azure サービス プリンシパルを次の Azure 組み込みロールに割り当てます。 接続するマシンがある Azure リソース グループにサービス プリンシパルを割り当てます。
役割 | 必要な操作 |
---|---|
Azure Connected Machine のリソース管理者または共同作成者 | リソース グループ内の Arc 対応 Nexus Kubernetes クラスター VM サーバーを接続し、Azure Monitoring Agent (AMA) をインストールする |
共同作成者の監視または共同作成者 | リソース グループにデータ収集規則 (DCR) を作成し、それに Arc 対応サーバーを関連付ける |
ユーザー アクセス管理者、およびリソース ポリシー共同作成者または共同作成者 | Azure ポリシー割り当てを使用して、DCR が Arc 対応マシンに関連付けられていることを確認する場合に必要 |
Kubernetes 拡張機能共同作成者 | Container Insights の K8s 拡張機能をデプロイするために必要 |
環境のセットアップ
含まれているスクリプトをコピーして実行します。 これらは、Azure portal の Azure Cloud Shell から実行できます。 または、Kubernetes コマンド ライン ツール (kubectl) と Azure CLI がインストールされている Linux コマンド プロンプトから実行することもできます。
含まれているスクリプトを実行する前に、次の環境変数を定義します。
環境変数 | 説明 |
---|---|
SUBSCRIPTION_ID | リソース グループを含む Azure サブスクリプションの ID |
RESOURCE_GROUP | Arc 対応サーバーと関連リソースが作成されるリソース グループ名 |
LOCATION | Arc 対応サーバーと関連リソースが作成される Azure リージョン |
SERVICE_PRINCIPAL_ID | 適切なロールの割り当てを持つ Azure サービス プリンシパルの appId |
SERVICE_PRINCIPAL_SECRET | Azure サービス プリンシパルの認証パスワード |
TENANT_ID | サービス プリンシパルが存在するテナント ディレクトリの ID |
PROXY_URL | Azure サービスへの接続に使用するプロキシ URL |
NAMESPACE | Kubernetes アーティファクトが作成される名前空間 |
便宜上、テンプレート ファイル (arc-connect.env
) を変更して環境変数の値を設定できます。
# Apply the modified values to the environment
./arc-connect.env
データ収集ルール (DCR) を追加する
Arc 対応サーバーを DCR に関連付けて、Log Analytics ワークスペースへのログ データの収集を有効にします。 DCR は、Azure portal または CLI を使用して作成できます。 VM からデータを収集する DCR の作成については、こちらを参照してください。
含まれる dcr.sh
スクリプトでは、指定されたリソース グループ内に、ログ収集を構成する DCR が作成されます。
適切な環境セットアップと、サービス プリンシパルのロールの前提条件を確認します。 DCR は指定したリソース グループに作成されます。
DCR に従ってログ データ インジェスト用の Log Analytics ワークスペースを作成または識別します。 環境変数 LAW_RESOURCE_ID をそのリソース ID に設定します。 既知の Log Analytics ワークスペース名のリソース ID を取得します。
export LAW_RESOURCE_ID=$(az monitor log-analytics workspace show -g "${RESOURCE_GROUP}" -n <law name> --query id -o tsv)
- dcr.sh スクリプトを実行します。 これは、指定したリソース グループに ${RESOURCE_GROUP}-syslog-dcr という名前の DCR を作成します
./dcr.sh
Azure portal または CLI から DCR を表示または管理します。 既定では、Linux Syslog ログ レベルは "INFO" に設定されています。 必要に応じてログ レベルを変更できます。
Note
手動でまたはポリシーを使用して、DCR の作成前に作成されたサーバーを関連付けます。 修復タスクに関する記事を参照してください。
Arc 対応サーバー リソースを DCR に関連付ける
ログを Log Analytics ワークスペースにフローさせるために、Arc 対応サーバー リソースを作成された DCR に関連付けます。 サーバーを DCR に関連付けるためのオプションがあります。
Azure portal または CLI を使用して選択した Arc 対応サーバーを DCR に関連付ける
Azure portal で、[リソース] セクションを使用して、Arc 対応サーバー リソースを DCR に追加します。
Azure CLI を使用したリソースの関連付けの詳細については、このリンクを使用してください。
Azure ポリシーを使用して DCR の関連付けを管理する
関連付けを適用するポリシーをリソース グループに割り当てます。 Linux Arc マシンを DCR に関連付ける組み込みのポリシー定義があります。 DCR をパラメーターとして使用して、リソース グループにポリシーを割り当てます。 これにより、リソース グループ内のすべての Arc 対応サーバーが同じ DCR に関連付けられます。
Azure portal で、[ポリシー定義] ページから Assign
ボタンを選択します。
利便性を高めるため、指定された assign.sh
スクリプトは、指定されたリソース グループと、dcr.sh
スクリプトで作成された DCR に組み込みポリシーを割り当てます。
- ポリシーとロールの割り当てを実行するために、適切な環境セットアップと、サービス プリンシパルのロールの前提条件を確認します。
- 「データ収集ルールの追加」セクションの説明に従って、
dcr.sh
スクリプトを使用して、リソース グループに DCR 作成します。 assign.sh
スクリプトを実行します。 ポリシーの割り当てと必要なロールの割り当てが作成されます。
./assign.sh
Azure Monitor エージェントをインストールする
付属の install.sh
を使用します。これにより、Nexus Kubernetes クラスターに Kubernetes daemonSet が作成されます。
各クラスター ノードにポッドをデプロイし、Azure Monitor エージェント (AMA) をインストールします。
daemonSet
には、サーバー接続と AMA プロセスを監視する liveness probe も含まれています。
Note
Azure Monitor エージェントをインストールするには、先に Nexus Kubernetes クラスター VM を Arc 対応にする必要があります。 最新のバージョン バンドルを使用している場合、このプロセスは自動的に行われます。 ただし、使用するバージョン バンドルでクラスター VM の Arc 登録が既定でサポートされていない場合は、クラスターを最新のバージョン バンドルにアップグレードする必要があります。 バージョン バンドルの詳細については、Nexus Kubernetes クラスターのサポートされているバージョンに関するページを参照してください。
- 「環境のセットアップ」で指定された環境を設定します。 Nexus Kubernetes クラスター VM の現在の
kubeconfig
コンテキストを設定します。 - Nexus Kubernetes クラスターへの
Kubectl
アクセスを許可します。Note
Nexus Kubernetes クラスターを作成すると、Nexus によってクラスター リソースの格納専用の管理対象リソース グループが自動的に作成され、このグループ内に Arc 接続クラスター リソースが確立されます。
kubeconfig
を設定する必要があります。 関連する Microsoft Entra エンティティを使用して Azure CLI にログインした後、それを囲むファイアウォールの外側であっても、どこからでもクラスターと通信するために必要なkubeconfig
を取得できます。CLUSTER_NAME
変数、RESOURCE_GROUP
変数、およびSUBSCRIPTION_ID
変数を設定します。CLUSTER_NAME="myNexusK8sCluster" RESOURCE_GROUP="myResourceGroup" SUBSCRIPTION_ID=<set the correct subscription_id>
az
を使用して管理対象リソース グループにクエリを実行し、MANAGED_RESOURCE_GROUP
に格納しますaz account set -s $SUBSCRIPTION_ID MANAGED_RESOURCE_GROUP=$(az networkcloud kubernetescluster show -n $CLUSTER_NAME -g $RESOURCE_GROUP --output tsv --query managedResourceGroupConfiguration.name)
次のコマンドは、指定された Nexus Kubernetes クラスターの Kubernetes API サーバーに接続できる connectedk8s プロキシを起動します。
az connectedk8s proxy -n $CLUSTER_NAME -g $MANAGED_RESOURCE_GROUP &
kubectl
を使用して、クラスターに要求を送信します。kubectl get pods -A
これで、すべてのノードの一覧が含まれているクラスターからの応答が表示されます。
注意
"アクセス トークンをクライアント プロキシに投稿できませんでした。MSI に接続できませんでした" というエラー メッセージが表示された場合は、
az login
を実行して Azure で再認証する必要がある場合があります。 - コマンド プロンプトから、Nexus Kubernetes クラスターへの kubectl アクセスを使用して
install.sh
スクリプトを実行します。
このスクリプトでは、クラスターに daemonSet
をデプロイします。 次のように進行状況を監視します。
# Run the install script and observe results
./install.sh
kubectl get pod --selector='name=naks-vm-telemetry'
kubectl logs <podname>
完了すると、"Server monitoring configured successfully" というメッセージがログに記録されます。
Note
これらの接続されたサーバーを DCR に関連付けます。 ポリシーを構成した後、Azure Log Analytics ワークスペースのログを監視するために多少の遅延が発生する場合があります
Nexus Kubernetes クラスターの監視 - K8s レイヤー
前提条件 - Kubernetes
オペレーターが Nexus Kubernetes クラスターで監視ツールを構成するために確認する必要がある前提条件がいくつかあります。
Container Insights では、そのデータを Log Analytics ワークスペースに保存します。 ログ データは、「データ収集ルール (DCR) の追加」セクションで説明されている初期スクリプトの実行中に指定したリソース ID を持つワークスペースにフローします。 それ以外の場合は、(Azure の場所に基づいて) サブスクリプションに関連付けられているリソース グループ内の既定のワークスペースにデータが流し込まれます。
米国東部の例を次に示します。
- Log Analytics ワークスペース名: DefaultWorkspace-<GUID>-EUS
- リソース グループ名: DefaultResourceGroup-EUS
既存の Log Analytics ワークスペースのリソース ID を取得するには、次のコマンドを実行します。
az login
az account set --subscription "<Subscription Name or ID the Log Analytics workspace is in>"
az monitor log-analytics workspace show --workspace-name "<Log Analytics workspace Name>" \
--resource-group "<Log Analytics workspace Resource Group>" \
-o tsv --query id
Container Insights をデプロイし、該当する Log Analytics ワークスペースにデータを表示するには、アカウントで特定のロールの割り当てが必要です。 たとえば、"共同作成者" ロールの割り当てです。 必要なロールを割り当てる手順を参照してください。
- Log Analytics 共同作成者ロール: CNF (プロビジョニング済み) クラスターでコンテナーの監視を有効にするために必要なアクセス許可。
- Log Analytics 閲覧者ロール: Log Analytics 共同作成者ロールの非メンバーは、コンテナーの監視を有効にすると、Log Analytics ワークスペース内のデータを表示するためのアクセス許可を受け取ります。
クラスター拡張機能をインストールする
Azure Cloud Shell にサインインして、クラスターにアクセスします。
az login
az account set --subscription "<Subscription Name or ID the Provisioned Cluster is in>"
次の 2 つのコマンドのいずれかを使用して、プロビジョニングされた Nexus Kubernetes クラスターに Container Insights 拡張機能をデプロイします。
顧客が事前に作成した Log Analytics ワークスペースを使用する
az k8s-extension create --name azuremonitor-containers \
--cluster-name "<Nexus Kubernetes cluster Name>" \
--resource-group "<Nexus Kubernetes cluster Resource Group>" \
--cluster-type connectedClusters \
--extension-type Microsoft.AzureMonitor.Containers \
--release-train preview \
--configuration-settings logAnalyticsWorkspaceResourceID="<Log Analytics workspace Resource ID>" \
amalogsagent.useAADAuth=true
既定の Log Analytics ワークスペースを使用する
az k8s-extension create --name azuremonitor-containers \
--cluster-name "<Nexus Kubernetes cluster Name>" \
--resource-group "<Nexus Kubernetes cluster Resource Group>" \
--cluster-type connectedClusters \
--extension-type Microsoft.AzureMonitor.Containers \
--release-train preview \
--configuration-settings amalogsagent.useAADAuth=true
クラスター拡張機能を検証する
次のコマンドを使用して、Nexus Kubernetes クラスターでの監視エージェントの有効化が正常にデプロイされたことを検証します。
az k8s-extension show --name azuremonitor-containers \
--cluster-name "<Nexus Kubernetes cluster Name>" \
--resource-group "<Nexus Kubernetes cluster Resource Group>" \
--cluster-type connectedClusters
拡張機能の "成功" のプロビジョニング状態を探します。 "k8s-extension create" コマンドも状態を返している可能性があります。
ログとメトリックの収集をカスタマイズする
Container Insights には、Nexus Kubernetes クラスターからのログとメトリックの収集を微調整するエンドユーザー機能が用意されています (「Container Insights のエージェント データ収集を構成する」)。
その他のリソース
- ブックのドキュメントを確認してから、Operator Nexus テレメトリ サンプル Operator Nexus ブックを使用できます。
- Azure Monitor アラート、Azure Monitor アラート ルールの作成方法を確認し、サンプルの Operator Nexus アラート テンプレートを使用します。
フィードバック
https://aka.ms/ContentUserFeedback」を参照してください。
以下は間もなく提供いたします。2024 年を通じて、コンテンツのフィードバック メカニズムとして GitHub の issue を段階的に廃止し、新しいフィードバック システムに置き換えます。 詳細については、「フィードバックの送信と表示