Loading deploy/tfs.sh +8 −0 Original line number Diff line number Diff line Loading @@ -340,6 +340,14 @@ for COMPONENT in $TFS_COMPONENTS; do sed -E -i "s#image: $GITLAB_REPO_URL/$COMPONENT:${VERSION}#image: $IMAGE_URL#g" "$MANIFEST" fi if [ "$COMPONENT" == "webui" ] && [[ "$TFS_COMPONENTS" == *"agentic"* ]]; then sed -E -i '/value: "\/webui\/"/ a\ - name: AGENTICSERVICE_SERVICE_HOST\ value: "agenticservice"\ - name: AGENTICSERVICE_SERVICE_PORT_HTTP\ value: "8800"' "$MANIFEST" fi sed -E -i "s#imagePullPolicy: .*#imagePullPolicy: Always#g" "$MANIFEST" # TODO: harmonize names of the monitoring component Loading manifests/agenticservice.yaml +1 −0 Original line number Diff line number Diff line Loading @@ -19,6 +19,7 @@ metadata: data: ADK_MODEL: "openai/gpt-4.1-mini" ADK_AGENT_GRAPH: "single" ADK_HTTP_ROOT_PATH: "/agentic" ADK_DOMAIN_ID: "A" ADK_DOMAIN_NAME: "domain-a" ADK_PEERS: "" Loading src/agentic/Config.py +13 −0 Original line number Diff line number Diff line Loading @@ -25,6 +25,7 @@ DEFAULT_AGENTIC_SPECTRUM_DB_PATH = "/var/lib/tfs-agentic/adk_spectrum.sqlite" DEFAULT_AGENTIC_A2A_TIMEOUT_SECONDS = "180" DEFAULT_AGENTIC_DEFAULT_SLOT_WIDTH = "16" DEFAULT_AGENTIC_DOMAIN_API_PORT = "8800" DEFAULT_AGENTIC_HTTP_ROOT_PATH = "/agentic" DEFAULT_AGENTIC_MCP_STARTUP_WARMUP_TIMEOUT_SECONDS = "10" DEFAULT_AGENTIC_MCP_TOOL_TIMEOUT_SECONDS = "30" DEFAULT_AGENTIC_RUN_TIMEOUT_SECONDS = "120" Loading @@ -50,6 +51,7 @@ ENVVAR_ADK_A2A_PUBLIC_URL = "ADK_A2A_PUBLIC_URL" ENVVAR_ADK_A2A_TIMEOUT_SECONDS = "ADK_A2A_TIMEOUT_SECONDS" ENVVAR_ADK_DEFAULT_SLOT_WIDTH = "ADK_DEFAULT_SLOT_WIDTH" ENVVAR_ADK_DOMAIN_API_PORT = "ADK_DOMAIN_API_PORT" ENVVAR_ADK_HTTP_ROOT_PATH = "ADK_HTTP_ROOT_PATH" ENVVAR_ADK_MODEL = "ADK_MODEL" ENVVAR_ADK_AGENT_GRAPH = "ADK_AGENT_GRAPH" ENVVAR_ADK_DOMAIN_ID = "ADK_DOMAIN_ID" Loading Loading @@ -201,6 +203,17 @@ def get_agentic_domain_api_port() -> int: ) def get_agentic_http_root_path() -> str: root_path = get_setting( ENVVAR_ADK_HTTP_ROOT_PATH, default=DEFAULT_AGENTIC_HTTP_ROOT_PATH, ) root_path = root_path.strip().rstrip("/") if not root_path: return "" return root_path if root_path.startswith("/") else f"/{root_path}" def get_agentic_graph_normalized() -> str: return get_agentic_graph().strip().lower() or DEFAULT_AGENTIC_GRAPH Loading src/agentic/README.md +61 −0 Original line number Diff line number Diff line Loading @@ -26,6 +26,7 @@ Server components are available: ```bash cd ~/tfs-ctrl TFS_COMPONENTS="context device pathcomp opticalcontroller service nbi webui mcp_server agentic" \ TFS_EXTRA_MANIFESTS="manifests/nginx_ingress_http.yaml" \ CRDB_DROP_DATABASE_IF_EXISTS=YES \ ./deploy/all.sh ``` Loading @@ -38,6 +39,13 @@ The deployment manifest creates: - `agenticservice`: HTTP service on port `8800`. - `tfs-ingress-agentic`: ingress path `/agentic`. When WebUI and Agentic are both selected in `TFS_COMPONENTS`, the TFS WebUI navigation bar exposes an `Agentic` entry. The link opens the Agentic service root through `/agentic`, which redirects to the generated FastAPI documentation under `/agentic/docs`. Expose the WebUI ingress with `manifests/nginx_ingress_http.yaml` to reach the TFS WebUI through `/webui/`. Do not commit real LLM API keys, MCP tokens, SSH keys, or controller credentials. Patch secrets at deployment time: Loading @@ -62,6 +70,8 @@ Main settings: - `ADK_MODEL`: LLM model identifier. Default is `openai/gpt-4.1-mini`. - `ADK_AGENT_GRAPH`: agent graph to run. Default is `single`; `granular` is kept for debugging and fallback. - `ADK_HTTP_ROOT_PATH`: HTTP prefix used when Agentic is exposed behind the TFS ingress. Default is `/agentic`. - `ADK_DOMAIN_ID`: short domain identifier such as `A`. - `ADK_DOMAIN_NAME`: human-readable domain name such as `domain-a`. - `ADK_PEERS`: comma-separated peer map in the form Loading Loading @@ -131,6 +141,19 @@ The component source is split into: `GET /health` returns component health, local domain ID, peer summary, session database health, and startup warm-up results. `GET /` redirects to the generated Agentic API documentation. Through the TFS ingress this is reachable as: ```text http://<controller-host>/agentic ``` or directly as: ```text http://<controller-host>/agentic/docs ``` `POST /agent/run` receives operator-facing natural-language requests: ```bash Loading Loading @@ -165,6 +188,44 @@ Diagnostic endpoints are also available for direct workflow tests: Prefer `/agent/run` for operator-facing validation. Use direct diagnostic endpoints only for integration tests and failure isolation. ## Google ADK WebUI Google ADK WebUI is intended for development and debugging of the agent graph. The production TFS component runs the Agentic FastAPI service on port `8800`; it does not start `adk web` as a second long-running process. The package exposes `agentic.agent:root_agent` so ADK Web can discover the same root agent used by the service. From a development checkout with the Agentic dependencies installed, start ADK Web from the directory containing the `agentic` package: ```bash cd ~/tfs-ctrl/src PYTHONPATH=. adk web --host 0.0.0.0 --port 8000 ``` Then open: ```text http://<development-host>:8000 ``` and select the `agentic` app. Use the same environment variables documented above, especially `ADK_MODEL`, `OPENAI_API_KEY`, `TFS_MCP_URL`, `ADK_DOMAIN_ID`, `ADK_PEERS`, and the session/spectrum database paths. For Kubernetes debugging, run ADK Web in a temporary debug pod or side process using the same image and environment as `agenticservice`, then expose or port-forward its port: ```bash kubectl -n tfs port-forward deployment/agenticservice 8800:8800 ``` The command above exposes the production Agentic API locally as `http://127.0.0.1:8800`. If a separate ADK Web debug process is started on port `8000`, port-forward that process instead and open `http://127.0.0.1:8000`. ## Smoke Tests After deployment, check health: Loading src/agentic/agent.py 0 → 100644 +17 −0 Original line number Diff line number Diff line # Copyright 2022-2026 ETSI SDG TeraFlowSDN (TFS) (https://tfs.etsi.org/) # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. from agentic.service.agent import root_agent __all__ = ("root_agent",) Loading
deploy/tfs.sh +8 −0 Original line number Diff line number Diff line Loading @@ -340,6 +340,14 @@ for COMPONENT in $TFS_COMPONENTS; do sed -E -i "s#image: $GITLAB_REPO_URL/$COMPONENT:${VERSION}#image: $IMAGE_URL#g" "$MANIFEST" fi if [ "$COMPONENT" == "webui" ] && [[ "$TFS_COMPONENTS" == *"agentic"* ]]; then sed -E -i '/value: "\/webui\/"/ a\ - name: AGENTICSERVICE_SERVICE_HOST\ value: "agenticservice"\ - name: AGENTICSERVICE_SERVICE_PORT_HTTP\ value: "8800"' "$MANIFEST" fi sed -E -i "s#imagePullPolicy: .*#imagePullPolicy: Always#g" "$MANIFEST" # TODO: harmonize names of the monitoring component Loading
manifests/agenticservice.yaml +1 −0 Original line number Diff line number Diff line Loading @@ -19,6 +19,7 @@ metadata: data: ADK_MODEL: "openai/gpt-4.1-mini" ADK_AGENT_GRAPH: "single" ADK_HTTP_ROOT_PATH: "/agentic" ADK_DOMAIN_ID: "A" ADK_DOMAIN_NAME: "domain-a" ADK_PEERS: "" Loading
src/agentic/Config.py +13 −0 Original line number Diff line number Diff line Loading @@ -25,6 +25,7 @@ DEFAULT_AGENTIC_SPECTRUM_DB_PATH = "/var/lib/tfs-agentic/adk_spectrum.sqlite" DEFAULT_AGENTIC_A2A_TIMEOUT_SECONDS = "180" DEFAULT_AGENTIC_DEFAULT_SLOT_WIDTH = "16" DEFAULT_AGENTIC_DOMAIN_API_PORT = "8800" DEFAULT_AGENTIC_HTTP_ROOT_PATH = "/agentic" DEFAULT_AGENTIC_MCP_STARTUP_WARMUP_TIMEOUT_SECONDS = "10" DEFAULT_AGENTIC_MCP_TOOL_TIMEOUT_SECONDS = "30" DEFAULT_AGENTIC_RUN_TIMEOUT_SECONDS = "120" Loading @@ -50,6 +51,7 @@ ENVVAR_ADK_A2A_PUBLIC_URL = "ADK_A2A_PUBLIC_URL" ENVVAR_ADK_A2A_TIMEOUT_SECONDS = "ADK_A2A_TIMEOUT_SECONDS" ENVVAR_ADK_DEFAULT_SLOT_WIDTH = "ADK_DEFAULT_SLOT_WIDTH" ENVVAR_ADK_DOMAIN_API_PORT = "ADK_DOMAIN_API_PORT" ENVVAR_ADK_HTTP_ROOT_PATH = "ADK_HTTP_ROOT_PATH" ENVVAR_ADK_MODEL = "ADK_MODEL" ENVVAR_ADK_AGENT_GRAPH = "ADK_AGENT_GRAPH" ENVVAR_ADK_DOMAIN_ID = "ADK_DOMAIN_ID" Loading Loading @@ -201,6 +203,17 @@ def get_agentic_domain_api_port() -> int: ) def get_agentic_http_root_path() -> str: root_path = get_setting( ENVVAR_ADK_HTTP_ROOT_PATH, default=DEFAULT_AGENTIC_HTTP_ROOT_PATH, ) root_path = root_path.strip().rstrip("/") if not root_path: return "" return root_path if root_path.startswith("/") else f"/{root_path}" def get_agentic_graph_normalized() -> str: return get_agentic_graph().strip().lower() or DEFAULT_AGENTIC_GRAPH Loading
src/agentic/README.md +61 −0 Original line number Diff line number Diff line Loading @@ -26,6 +26,7 @@ Server components are available: ```bash cd ~/tfs-ctrl TFS_COMPONENTS="context device pathcomp opticalcontroller service nbi webui mcp_server agentic" \ TFS_EXTRA_MANIFESTS="manifests/nginx_ingress_http.yaml" \ CRDB_DROP_DATABASE_IF_EXISTS=YES \ ./deploy/all.sh ``` Loading @@ -38,6 +39,13 @@ The deployment manifest creates: - `agenticservice`: HTTP service on port `8800`. - `tfs-ingress-agentic`: ingress path `/agentic`. When WebUI and Agentic are both selected in `TFS_COMPONENTS`, the TFS WebUI navigation bar exposes an `Agentic` entry. The link opens the Agentic service root through `/agentic`, which redirects to the generated FastAPI documentation under `/agentic/docs`. Expose the WebUI ingress with `manifests/nginx_ingress_http.yaml` to reach the TFS WebUI through `/webui/`. Do not commit real LLM API keys, MCP tokens, SSH keys, or controller credentials. Patch secrets at deployment time: Loading @@ -62,6 +70,8 @@ Main settings: - `ADK_MODEL`: LLM model identifier. Default is `openai/gpt-4.1-mini`. - `ADK_AGENT_GRAPH`: agent graph to run. Default is `single`; `granular` is kept for debugging and fallback. - `ADK_HTTP_ROOT_PATH`: HTTP prefix used when Agentic is exposed behind the TFS ingress. Default is `/agentic`. - `ADK_DOMAIN_ID`: short domain identifier such as `A`. - `ADK_DOMAIN_NAME`: human-readable domain name such as `domain-a`. - `ADK_PEERS`: comma-separated peer map in the form Loading Loading @@ -131,6 +141,19 @@ The component source is split into: `GET /health` returns component health, local domain ID, peer summary, session database health, and startup warm-up results. `GET /` redirects to the generated Agentic API documentation. Through the TFS ingress this is reachable as: ```text http://<controller-host>/agentic ``` or directly as: ```text http://<controller-host>/agentic/docs ``` `POST /agent/run` receives operator-facing natural-language requests: ```bash Loading Loading @@ -165,6 +188,44 @@ Diagnostic endpoints are also available for direct workflow tests: Prefer `/agent/run` for operator-facing validation. Use direct diagnostic endpoints only for integration tests and failure isolation. ## Google ADK WebUI Google ADK WebUI is intended for development and debugging of the agent graph. The production TFS component runs the Agentic FastAPI service on port `8800`; it does not start `adk web` as a second long-running process. The package exposes `agentic.agent:root_agent` so ADK Web can discover the same root agent used by the service. From a development checkout with the Agentic dependencies installed, start ADK Web from the directory containing the `agentic` package: ```bash cd ~/tfs-ctrl/src PYTHONPATH=. adk web --host 0.0.0.0 --port 8000 ``` Then open: ```text http://<development-host>:8000 ``` and select the `agentic` app. Use the same environment variables documented above, especially `ADK_MODEL`, `OPENAI_API_KEY`, `TFS_MCP_URL`, `ADK_DOMAIN_ID`, `ADK_PEERS`, and the session/spectrum database paths. For Kubernetes debugging, run ADK Web in a temporary debug pod or side process using the same image and environment as `agenticservice`, then expose or port-forward its port: ```bash kubectl -n tfs port-forward deployment/agenticservice 8800:8800 ``` The command above exposes the production Agentic API locally as `http://127.0.0.1:8800`. If a separate ADK Web debug process is started on port `8000`, port-forward that process instead and open `http://127.0.0.1:8000`. ## Smoke Tests After deployment, check health: Loading
src/agentic/agent.py 0 → 100644 +17 −0 Original line number Diff line number Diff line # Copyright 2022-2026 ETSI SDG TeraFlowSDN (TFS) (https://tfs.etsi.org/) # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. from agentic.service.agent import root_agent __all__ = ("root_agent",)