diff --git a/.github/scripts/agent-deploy.py b/.github/scripts/agent-deploy.py deleted file mode 100644 index eb3be137f..000000000 --- a/.github/scripts/agent-deploy.py +++ /dev/null @@ -1,80 +0,0 @@ -import argparse -import json -import os -import requests -from google.cloud import storage -import yaml - -def main(environment): - if environment.startswith("v10-"): - environment = environment.replace("v10-", "") - - gcp_key = json.loads(os.environ.get("GCP_KEY")) - storage_client = storage.Client.from_service_account_info(gcp_key) - - bucket_name = "utmstack-updates" - bucket = storage_client.bucket(bucket_name) - - # Read utmstack version from version.yml - with open(os.path.join(os.environ["GITHUB_WORKSPACE"], "version.yml"), "r") as f: - local_master_version = yaml.safe_load(f)['version'] - - # Read agent services version from versions.json - with open(os.path.join(os.environ["GITHUB_WORKSPACE"], "agent", "versions.json"), "r") as f: - local_agent_versions = json.load(f) - - # Download versions.json from URL - endp = "agent_updates/{}".format(environment) - response = requests.get("https://storage.googleapis.com/" + bucket_name + "/" + endp + "/versions.json") - remote_versions = response.json()['versions'] - - # Find the object with matching master_version - version_found = False - for obj in remote_versions: - if obj['master_version'] == local_master_version: - obj['agent_version'] = local_agent_versions["agent_version"] - obj['updater_version'] = local_agent_versions["updater_version"] - obj['redline_version'] = local_agent_versions["redline_version"] - version_found = True - break - - # If no matching object found, create a new one - if version_found == False: - version_obj = { - 'master_version': local_master_version, - 'agent_version': local_agent_versions["agent_version"], - 'updater_version': local_agent_versions["updater_version"], - 'redline_version': local_agent_versions["redline_version"], - } - remote_versions.append(version_obj) - - # Update version.json - version_blob = bucket.blob(endp + "/versions.json") - version_blob.upload_from_string(json.dumps({'versions': remote_versions}, indent=4)) - - # Create agent blobs - agent_windows_blob = bucket.blob(endp + "/agent_service/v" + local_agent_versions["agent_version"] + "/utmstack_agent_service.exe") - agent_linux_blob = bucket.blob(endp + "/agent_service/v" + local_agent_versions["agent_version"] + "/utmstack_agent_service") - updater_windows_blob = bucket.blob(endp + "/updater_service/v" + local_agent_versions["updater_version"] + "/utmstack_updater_service.exe") - updater_linux_blob = bucket.blob(endp + "/updater_service/v" + local_agent_versions["updater_version"] + "/utmstack_updater_service") - redline_windows_blob = bucket.blob(endp + "/redline_service/v" + local_agent_versions["redline_version"] + "/utmstack_redline_service.exe") - redline_linux_blob = bucket.blob(endp + "/redline_service/v" + local_agent_versions["redline_version"] + "/utmstack_redline_service") - installer_windows_blob = bucket.blob(endp + "/installer/v" + local_master_version + "/utmstack_agent_installer.exe") - installer_linux_blob = bucket.blob(endp + "/installer/v" + local_master_version + "/utmstack_agent_installer") - - # Upload agent services - agent_windows_blob.upload_from_filename(os.path.join(os.environ["GITHUB_WORKSPACE"], "agent", "agent", "utmstack_agent_service.exe")) - agent_linux_blob.upload_from_filename(os.path.join(os.environ["GITHUB_WORKSPACE"], "agent", "agent", "utmstack_agent_service")) - updater_windows_blob.upload_from_filename(os.path.join(os.environ["GITHUB_WORKSPACE"], "agent", "updater", "utmstack_updater_service.exe")) - updater_linux_blob.upload_from_filename(os.path.join(os.environ["GITHUB_WORKSPACE"], "agent", "updater", "utmstack_updater_service")) - redline_windows_blob.upload_from_filename(os.path.join(os.environ["GITHUB_WORKSPACE"], "agent", "redline", "utmstack_redline_service.exe")) - redline_linux_blob.upload_from_filename(os.path.join(os.environ["GITHUB_WORKSPACE"], "agent", "redline", "utmstack_redline_service")) - installer_windows_blob.upload_from_filename(os.path.join(os.environ["GITHUB_WORKSPACE"], "agent", "installer", "utmstack_agent_installer.exe")) - installer_linux_blob.upload_from_filename(os.path.join(os.environ["GITHUB_WORKSPACE"], "agent", "installer", "utmstack_agent_installer")) - -if __name__ == "__main__": - parser = argparse.ArgumentParser(description="Update UTMStack agents in Google Cloud Storage") - parser.add_argument("environment", type=str, help="Environment(dev, rc, release)") - - args = parser.parse_args() - main(args.environment) \ No newline at end of file diff --git a/.github/workflows/alpha-deployment.yml b/.github/workflows/alpha-deployment.yml index 06fa407da..0f6f11ab6 100644 --- a/.github/workflows/alpha-deployment.yml +++ b/.github/workflows/alpha-deployment.yml @@ -22,23 +22,32 @@ jobs: if [[ "${{ github.event.inputs.version_tag }}" =~ ^v[0-9]+\.[0-9]+\.[0-9]+-alpha\.[0-9]+$ ]]; then echo "✅ Version tag format is correct." - if [[ "${ github.ref }" =~ ^refs/heads/(release/|feature/) ]]; then - echo "✅ Base branch ${ github.ref } is valid." + if [[ "${{ github.ref }}" =~ ^refs/heads/(release/|feature/) ]]; then + echo "✅ Base branch ${{ github.ref }} is valid." else - echo "⛔ ERROR: Base branch ${ github.ref } is not valid. It should be release/ or feature/." + echo "⛔ ERROR: Base branch ${{ github.ref }} is not valid. It should be release/ or feature/." exit 1 fi echo "Validating user permissions..." - RESPONSE=$(curl -s -H "Authorization: Bearer ${{ secrets.GITHUB_TOKEN }}" \ + RESPONSE=$(curl -s -H "Authorization: Bearer ${{ secrets.API_SECRET }}" \ -H "Accept: application/vnd.github.json" \ "https://api.github.com/orgs/utmstack/teams/integration-developers/memberships/${{ github.actor }}") if echo "$RESPONSE" | grep -q '"state": "active"'; then echo "✅ User ${{ github.actor }} is a member of the integration-developers team." else - echo "⛔ ERROR: User ${{ github.actor }} is not a member of the integration-developers team." - exit 1 + RESPONSE=$(curl -s -H "Authorization: Bearer ${{ secrets.API_SECRET }}" \ + -H "Accept: application/vnd.github.json" \ + "https://api.github.com/orgs/utmstack/teams/core-developers/memberships/${{ github.actor }}") + + if echo "$RESPONSE" | grep -q '"state": "active"'; then + echo "✅ User ${{ github.actor }} is a member of the core-developers team." + else + echo "⛔ ERROR: User ${{ github.actor }} is not a member of the core-developers or integration-developers team." + echo $RESPONSE + exit 1 + fi fi else @@ -47,17 +56,16 @@ jobs: fi deploy: - name: Deploy + name: Deploy to Alpha needs: validations uses: ./.github/workflows/build.yml with: version_tag: ${{ github.event.inputs.version_tag }} event_processor_tag: ${{ github.event.inputs.event_processor_tag }} environment: alpha - ghcr_token: ${{ secrets.GITHUB_TOKEN }} - sign_cert: ${{ vars.SIGN_CERT }} - sign_key: ${{ secrets.SIGN_KEY }} - sign_container: ${{ secrets.SIGN_CONTAINER }} - env: + secrets: + AGENT_SECRET_PREFIX: ${{ secrets.AGENT_SECRET_PREFIX }} + SIGN_KEY: ${{ secrets.SIGN_KEY }} + SIGN_CONTAINER: ${{ secrets.SIGN_CONTAINER }} CM_AUTH: ${{ secrets.CM_AUTH_ALPHA }} \ No newline at end of file diff --git a/.github/workflows/beta-deployment.yml b/.github/workflows/beta-deployment.yml index dc7b7eeb1..8042aff8e 100644 --- a/.github/workflows/beta-deployment.yml +++ b/.github/workflows/beta-deployment.yml @@ -22,10 +22,10 @@ jobs: if [[ "${{ github.event.inputs.version_tag }}" =~ ^v[0-9]+\.[0-9]+\.[0-9]+-beta\.[0-9]+$ ]]; then echo "✅ Version tag format is correct." - if [[ "${ github.ref }" =~ ^refs/heads/(release/|feature/) ]]; then - echo "✅ Base branch ${ github.ref } is valid." + if [[ "${{ github.ref }}" =~ ^refs/heads/(release/|feature/) ]]; then + echo "✅ Base branch ${{ github.ref }} is valid." else - echo "⛔ ERROR: Base branch ${ github.ref } is not valid. It should be release/ or feature/." + echo "⛔ ERROR: Base branch ${{ github.ref }} is not valid. It should be release/ or feature/." exit 1 fi @@ -38,7 +38,7 @@ jobs: echo "✅ User ${{ github.actor }} is a member of the core-developers team." else echo "⛔ ERROR: User ${{ github.actor }} is not a member of the core-developers team." - exit 1 + exit 1 fi else @@ -47,17 +47,16 @@ jobs: fi deploy: - name: Deploy + name: Deploy to Beta needs: validations uses: ./.github/workflows/build.yml with: version_tag: ${{ github.event.inputs.version_tag }} event_processor_tag: ${{ github.event.inputs.event_processor_tag }} environment: beta - ghcr_token: ${{ secrets.GITHUB_TOKEN }} - sign_cert: ${{ vars.SIGN_CERT }} - sign_key: ${{ secrets.SIGN_KEY }} - sign_container: ${{ secrets.SIGN_CONTAINER }} - env: - CM_AUTH: ${{ secrets.CM_AUTH_BETA }} + secrets: + AGENT_SECRET_PREFIX: ${{ secrets.AGENT_SECRET_PREFIX }} + SIGN_KEY: ${{ secrets.SIGN_KEY }} + SIGN_CONTAINER: ${{ secrets.SIGN_CONTAINER }} + CM_AUTH: ${{ secrets.CM_AUTH_ALPHA }} \ No newline at end of file diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 71c0eb9d6..7274af7d1 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -12,18 +12,16 @@ on: environment: required: true type: string - ghcr_token: + secrets: + AGENT_SECRET_PREFIX: required: true - type: string - sign_cert: + SIGN_KEY: required: true - type: string - sign_key: + SIGN_CONTAINER: required: true - type: string - sign_container: + CM_AUTH: required: true - type: string + jobs: build_images: @@ -49,7 +47,7 @@ jobs: - name: Login to GitHub Container Registry run: | - docker login ghcr.io -u utmstack -p ${{ inputs.ghcr_token }} + docker login ghcr.io -u utmstack -p ${{ secrets.GITHUB_TOKEN }} echo "Logged in to GitHub Container Registry" - name: Download base images @@ -59,47 +57,53 @@ jobs: - name: Build Agent run: | - cd ${{ github.workspace }}/agent/service/config; (Get-Content const.go) | Foreach-Object { $_ -replace 'const REPLACE_KEY string = ""', 'const REPLACE_KEY string = "${{ secrets.AGENT_SECRET_PREFIX }}"' } | Set-Content const.go + cd ${{ github.workspace }}/agent/config; (Get-Content const.go) | Foreach-Object { $_ -replace 'const REPLACE_KEY string = ""', 'const REPLACE_KEY string = "${{ secrets.AGENT_SECRET_PREFIX }}"' } | Set-Content const.go - $env:GOOS = "linux" $env:GOARCH = "amd64" - cd ${{ github.workspace }}/agent/service; go build -o utmstack_agent_service -v . - cd ${{ github.workspace }}/agent/installer; go build -o utmstack_agent_installer -v . - + $env:GOOS = "linux" + cd ${{ github.workspace }}/agent + go build -o utmstack_agent -v . + $env:GOOS = "windows" - cd ${{ github.workspace }}/agent/service; go build -o utmstack_agent_service.exe -v . - signtool sign /fd SHA256 /tr http://timestamp.digicert.com /td SHA256 /f "${{ inputs.sign_cert }}" /csp "eToken Base Cryptographic Provider" /k "[{{${{ inputs.sign_key }}}}]=${{ inputs.sign_container }}" "utmstack_agent_service.exe" - cd ${{ github.workspace }}/agent/installer; go build -o utmstack_agent_installer.exe -v . - signtool sign /fd SHA256 /tr http://timestamp.digicert.com /td SHA256 /f "${{ inputs.sign_cert }}" /csp "eToken Base Cryptographic Provider" /k "[{{${{ inputs.sign_key }}}}]=${{ inputs.sign_container }}" "utmstack_agent_installer.exe" + go build -o utmstack_agent.exe -v . + signtool sign /fd SHA256 /tr http://timestamp.digicert.com /td SHA256 /f "${{ vars.SIGN_CERT }}" /csp "eToken Base Cryptographic Provider" /k "[{{${{ secrets.SIGN_KEY }}}}]=${{ secrets.SIGN_CONTAINER }}" "utmstack_agent.exe" + New-Item -ItemType Directory -Force -Path "./dependencies/" Copy-Item -Path "C:/dependencies/${{ inputs.environment }}/agent/*" -Destination "./dependencies/" echo "Agent build completed" - name: Build Plugins run: | - export GOOS=linux - export GOARCH=amd64 - cd ${{ github.workspace }}/plugins - make build + $env:GOOS = "linux" + $env:GOARCH = "amd64" + cd ${{ github.workspace }}/plugins/alerts; go build -o com.utmstack.alerts.plugin -v . + cd ${{ github.workspace }}/plugins/aws; go build -o com.utmstack.aws.plugin -v . + cd ${{ github.workspace }}/plugins/azure; go build -o com.utmstack.azure.plugin -v . + cd ${{ github.workspace }}/plugins/bitdefender; go build -o com.utmstack.bitdefender.plugin -v . + cd ${{ github.workspace }}/plugins/config; go build -o com.utmstack.config.plugin -v . + cd ${{ github.workspace }}/plugins/events; go build -o com.utmstack.events.plugin -v . + cd ${{ github.workspace }}/plugins/gcp; go build -o com.utmstack.gcp.plugin -v . + cd ${{ github.workspace }}/plugins/geolocation; go build -o com.utmstack.geolocation.plugin -v . + cd ${{ github.workspace }}/plugins/inputs; go build -o com.utmstack.inputs.plugin -v . + cd ${{ github.workspace }}/plugins/o365; go build -o com.utmstack.o365.plugin -v . + cd ${{ github.workspace }}/plugins/sophos; go build -o com.utmstack.sophos.plugin -v . + cd ${{ github.workspace }}/plugins/stats; go build -o com.utmstack.stats.plugin -v . - name: Build Event Processor Image run: | New-Item -ItemType Directory -Force -Path "./geolocation/" Copy-Item -Path "C:/dependencies/${{ inputs.environment }}/geolocation/*" -Destination "./geolocation/" - - docker build -t ghcr.io/utmstack/utmstack/eventprocessor:${{ inputs.version_tag }}-community \ - --build-arg BASE_IMAGE=ghcr.io/threatwinds/eventprocessor/base:${{ inputs.event_processor_tag }} \ - -f ./event_processor.Dockerfile \ - . + docker build -t ghcr.io/utmstack/utmstack/eventprocessor:${{ inputs.version_tag }}-community --build-arg BASE_IMAGE=ghcr.io/threatwinds/eventprocessor/base:${{ inputs.event_processor_tag }} -f ./event_processor.Dockerfile . echo "Event Processor image built" - name: Build Agent Manager Image run: | - go build -o ./agent-manager/agent-manager -v ./agent-manager - docker build -t ghcr.io/utmstack/utmstack/agent-manager:${{ inputs.version_tag }}-community \ - -f ./agent-manager/Dockerfile \ - . + $env:GOOS = "linux" + $env:GOARCH = "amd64" + cd ${{ github.workspace }}/agent-manager; go build -o agent-manager -v . + cd ${{ github.workspace }} + docker build -t ghcr.io/utmstack/utmstack/agent-manager:${{ inputs.version_tag }}-community -f ./agent-manager/Dockerfile . echo "Agent Manager image built" - name: Push images with dependencies @@ -112,11 +116,12 @@ jobs: run: | echo "Pushing new release..." $changelog = Get-Content -Path "CHANGELOG.md" -Raw + $changelog = [string]$changelog - $cmAuth = $env:CM_AUTH | ConvertFrom-Json + $cmAuth = '${{ secrets.CM_AUTH }}' | ConvertFrom-Json $body = @{ - version = ${{ inputs.version_tag }} + version = '${{ inputs.version_tag }}' changelog = $changelog images = "ghcr.io/utmstack/utmstack/backend,ghcr.io/utmstack/utmstack/frontend,ghcr.io/utmstack/utmstack/user-auditor,ghcr.io/utmstack/utmstack/web-pdf,ghcr.io/utmstack/utmstack/eventprocessor,ghcr.io/utmstack/utmstack/agent-manager" edition = "community" @@ -131,4 +136,4 @@ jobs: -Body $body ` -ContentType "application/json" - $response + $response \ No newline at end of file diff --git a/.github/workflows/images-without-dependencies.yml b/.github/workflows/images-without-dependencies.yml index e8cf5a51c..1e30ff742 100644 --- a/.github/workflows/images-without-dependencies.yml +++ b/.github/workflows/images-without-dependencies.yml @@ -57,7 +57,7 @@ jobs: name: Java 11 deployment needs: prepare_deployment if: ${{ needs.prepare_deployment.outputs.tech == 'java-11' }} - uses: ./.github/workflows/used-docker-java-11.yml + uses: ./.github/workflows/used-docker-java-11-new.yml with: image_name: ${{ inputs.microservice }} tag: ${{inputs.tag}}-community @@ -70,4 +70,4 @@ jobs: uses: ./.github/workflows/used-docker-java.yml with: image_name: ${{ inputs.microservice }} - environment: ${{inputs.tag}}-community + environment: ${{inputs.tag}}-community \ No newline at end of file diff --git a/.github/workflows/principal-agent.yml b/.github/workflows/principal-agent.yml deleted file mode 100644 index 83bee2a0d..000000000 --- a/.github/workflows/principal-agent.yml +++ /dev/null @@ -1,94 +0,0 @@ -name: Agent Build - -on: - release: - types: [ 'released' ] - push: - branches: [ 'main', 'feature/**' ] - paths: - - 'agent/**' - - 'version.yml' - pull_request_review: - types: [submitted] - paths: - - 'agent/**' - - 'version.yml' - -jobs: - check: - name: Checking - runs-on: ubuntu-latest - outputs: - env_version: ${{ steps.set-env.outputs.env_version }} - steps: - - name: Determine Build Environment - id: set-env - run: | - if ${{ github.event_name == 'push' && startsWith(github.ref, 'refs/heads/feature/') }}; then - echo "DEV environment" - echo "env_version=v10-dev" >> $GITHUB_OUTPUT - elif ${{ github.event_name == 'pull_request_review' && github.event.review.state == 'approved' && github.event.pull_request.base.ref == 'main' && startsWith(github.event.pull_request.head.ref, 'feature/') }}; then - echo "QA environment" - echo "env_version=v10-qa" >> $GITHUB_OUTPUT - elif ${{ github.event_name == 'push' && github.ref == 'refs/heads/main' }}; then - echo "RC environment" - echo "env_version=v10-rc" >> $GITHUB_OUTPUT - elif ${{ github.event_name == 'release' }}; then - echo "RELEASE environment" - echo "env_version=release" >> $GITHUB_OUTPUT - fi - - build: - name: Build - needs: check - if: needs.check.outputs.env_version != '' - runs-on: signing - steps: - - name: Checkout code - uses: actions/checkout@v4 - - - name: Set up Go - uses: actions/setup-go@v5 - with: - go-version: 1.21 - - - name: Set up Python - uses: actions/setup-python@v5 - with: - python-version: '3.12' - - - name: Build and sign agent services - id: set-env - run: | - $env:DEPLOY_ENV = '${{ needs.check.outputs.env_version }}' - - cd ${{ github.workspace }}/agent/agent/configuration; (Get-Content const.go) | Foreach-Object { $_ -replace 'const REPLACE_KEY string = ""', 'const REPLACE_KEY string = "${{ secrets.AGENT_SECRET_PREFIX }}"' } | Set-Content const.go - - $env:GOOS = "linux" - $env:GOARCH = "amd64" - cd ${{ github.workspace }}/agent/agent; go build -o utmstack_agent_service -v . - cd ${{ github.workspace }}/agent/installer; go build -o utmstack_agent_installer -v . - cd ${{ github.workspace }}/agent/redline; go build -o utmstack_redline_service -v . - cd ${{ github.workspace }}/agent/updater; go build -o utmstack_updater_service -v . - - $env:GOOS = "windows" - cd ${{ github.workspace }}/agent/agent; go build -o utmstack_agent_service.exe -v . - signtool sign /fd SHA256 /tr http://timestamp.digicert.com /td SHA256 /f "${{ vars.SIGN_CERT }}" /csp "eToken Base Cryptographic Provider" /k "[{{${{ secrets.SIGN_KEY }}}}]=${{ secrets.SIGN_CONTAINER }}" "utmstack_agent_service.exe" - cd ${{ github.workspace }}/agent/installer; go build -o utmstack_agent_installer.exe -v . - signtool sign /fd SHA256 /tr http://timestamp.digicert.com /td SHA256 /f "${{ vars.SIGN_CERT }}" /csp "eToken Base Cryptographic Provider" /k "[{{${{ secrets.SIGN_KEY }}}}]=${{ secrets.SIGN_CONTAINER }}" "utmstack_agent_installer.exe" - cd ${{ github.workspace }}/agent/redline; go build -o utmstack_redline_service.exe -v . - signtool sign /fd SHA256 /tr http://timestamp.digicert.com /td SHA256 /f "${{ vars.SIGN_CERT }}" /csp "eToken Base Cryptographic Provider" /k "[{{${{ secrets.SIGN_KEY }}}}]=${{ secrets.SIGN_CONTAINER }}" "utmstack_redline_service.exe" - cd ${{ github.workspace }}/agent/updater; go build -o utmstack_updater_service.exe -v . - signtool sign /fd SHA256 /tr http://timestamp.digicert.com /td SHA256 /f "${{ vars.SIGN_CERT }}" /csp "eToken Base Cryptographic Provider" /k "[{{${{ secrets.SIGN_KEY }}}}]=${{ secrets.SIGN_CONTAINER }}" "utmstack_updater_service.exe" - - Invoke-WebRequest -Uri "https://www.python.org/ftp/python/3.12.1/python-3.12.1-amd64.exe" -OutFile "python-installer.exe" - Start-Process -FilePath "python-installer.exe" -ArgumentList "/quiet InstallAllUsers=1 PrependPath=1" -Wait - Remove-Item -Path "python-installer.exe" - python -m pip install --upgrade pip - pip install requests google-cloud-storage pyyaml - - $env:GCP_KEY = '${{ secrets.GCP_KEY }}' - cd ${{ github.workspace }}/.github/scripts; & 'C:\Program Files\Python312\python.exe' 'agent-deploy.py' $env:DEPLOY_ENV - - cd ${{ github.workspace }}; Remove-Item -Path "./*" -Recurse -Force - \ No newline at end of file diff --git a/.github/workflows/principal-installer-dev.yml b/.github/workflows/principal-installer-dev.yml deleted file mode 100644 index 82e8fe705..000000000 --- a/.github/workflows/principal-installer-dev.yml +++ /dev/null @@ -1,41 +0,0 @@ -name: Installer Dev - -on: - workflow_run: - workflows: ["Multi Environment Build"] - types: - - completed - -jobs: - check_feature: - name: Check if feature - runs-on: ubuntu-latest - outputs: - is_feature: ${{ steps.check.outputs.is_feature }} - steps: - - id: check - run: | - echo "Doing ${{ github.event.workflow_run.event }} on ${{ github.event.workflow_run.head_branch }}" - if ${{ github.event.workflow_run.event == 'push' && startsWith(github.event.workflow_run.head_branch, 'feature/') }}; then - echo "It's a feature" - echo "is_feature=true" >> $GITHUB_OUTPUT - else - echo "It's not a feature" - echo "is_feature=false" >> $GITHUB_OUTPUT - fi - deploy: - name: Deploy to dev - needs: check_feature - if: needs.check_feature.outputs.is_feature == 'true' - runs-on: dev - steps: - - name: Run - working-directory: /home/utmstack - run: | - sudo ./installer - - - name: Open ports - id: open_ports - working-directory: /home/utmstack - run: | - sudo docker service update --publish-add 9200:9200 utmstack_node1 & docker service update --publish-add 5432:5432 utmstack_postgres diff --git a/.github/workflows/principal-multi-env.yml b/.github/workflows/principal-multi-env.yml index 1fabb67a4..5cbeedfdc 100644 --- a/.github/workflows/principal-multi-env.yml +++ b/.github/workflows/principal-multi-env.yml @@ -4,9 +4,7 @@ on: release: types: [ 'released' ] push: - branches: [ 'main', 'feature/**' ] - pull_request_review: - types: [submitted] + branches: [ 'main' ] jobs: setup_deployment: @@ -19,13 +17,7 @@ jobs: - name: Determine Build Environment id: set-env run: | - if ${{ github.event_name == 'push' && startsWith(github.ref, 'refs/heads/feature/') }}; then - echo "DEV environment" - echo "env_version=v10-dev" >> $GITHUB_OUTPUT - elif ${{ github.event_name == 'pull_request_review' && github.event.review.state == 'approved' && github.event.pull_request.base.ref == 'main' && startsWith(github.event.pull_request.head.ref, 'feature/') }}; then - echo "QA environment" - echo "env_version=v10-qa" >> $GITHUB_OUTPUT - elif ${{ github.event_name == 'push' && github.ref == 'refs/heads/main' }}; then + if ${{ github.event_name == 'push' && github.ref == 'refs/heads/main' }}; then echo "RC environment" echo "env_version=v10-rc" >> $GITHUB_OUTPUT elif ${{ github.event_name == 'release' }}; then @@ -33,48 +25,70 @@ jobs: echo "env_version=v10" >> $GITHUB_OUTPUT fi - - uses: actions/checkout@v4 - - uses: dorny/paths-filter@v3 - id: filter - with: - filters: | - agent-manager: agent-manager/** - aws: aws/** - backend: - - 'backend/**' - - 'version.yml' - correlation: correlation/** - frontend: frontend/** - bitdefender: bitdefender/** - mutate: mutate/** - office365: office365/** - log-auth-proxy: log-auth-proxy/** - sophos: sophos/** - user-auditor: user-auditor/** - web-pdf: web-pdf/** - - runner: - name: Deployment + build_agent: + name: Build Agent-Manager Image & Agent & Dependencies needs: setup_deployment - if: ${{ needs.setup_deployment.outputs.microservices != '[]' && needs.setup_deployment.outputs.env_version != ''}} - strategy: - fail-fast: false - matrix: - service: ${{ fromJson(needs.setup_deployment.outputs.microservices) }} - uses: ./.github/workflows/used-runner.yml - with: - microservice: ${{ matrix.service }} - environment: ${{ needs.setup_deployment.outputs.env_version }} - secrets: inherit - + if: ${{ needs.setup_deployment.outputs.env_version != '' }} + runs-on: signing + steps: + - name: Check out code into the right branch + uses: actions/checkout@v4 + + - name: Login to GitHub Container Registry + run: | + docker login ghcr.io -u utmstack -p ${{ secrets.GITHUB_TOKEN }} + echo "Logged in to GitHub Container Registry" + + - name: Build Agent + run: | + cd ${{ github.workspace }}/agent/config; (Get-Content const.go) | Foreach-Object { $_ -replace 'const REPLACE_KEY string = ""', 'const REPLACE_KEY string = "${{ secrets.AGENT_SECRET_PREFIX }}"' } | Set-Content const.go + cd ${{ github.workspace }}/agent + + $env:GOOS = "linux" + $env:GOARCH = "amd64" + go build -o utmstack_agent_service -v . + # $env:GOARCH = "arm64" + # go build -o utmstack_agent_service_arm64 -v . + + $env:GOOS = "windows" + $env:GOARCH = "amd64" + go build -o utmstack_agent_service.exe -v . + signtool sign /fd SHA256 /tr http://timestamp.digicert.com /td SHA256 /f "${{ vars.SIGN_CERT }}" /csp "eToken Base Cryptographic Provider" /k "[{{${{ secrets.SIGN_KEY }}}}]=${{ secrets.SIGN_CONTAINER }}" "utmstack_agent_service.exe" + # $env:GOARCH = "arm64" + # go build -o utmstack_agent_service_arm64.exe -v . + # signtool sign /fd SHA256 /tr http://timestamp.digicert.com /td SHA256 /f "${{ vars.SIGN_CERT }}" /csp "eToken Base Cryptographic Provider" /k "[{{${{ secrets.SIGN_KEY }}}}]=${{ secrets.SIGN_CONTAINER }}" "utmstack_agent_service_arm64.exe" + + echo "Agent build completed" + + - name: Build & Push Agent Manager Image + run: | + $env:GOOS = "linux" + $env:GOARCH = "amd64" + cd ${{ github.workspace }}/agent-manager; go build -o agent-manager -v . + + New-Item -ItemType Directory -Force -Path "./dependencies/collector/" + Copy-Item -Path "C:/dependencies/${{ needs.setup_deployment.outputs.env_version }}/collector/*" -Destination "./dependencies/collector/" + + New-Item -ItemType Directory -Force -Path "./dependencies/agent/" + Copy-Item -Path "C:/dependencies/${{ needs.setup_deployment.outputs.env_version }}/agent/*" -Destination "./dependencies/agent/" + Copy-Item -Path "${{ github.workspace }}/agent/utmstack_agent_service" -Destination "./dependencies/agent/" + # Copy-Item -Path "${{ github.workspace }}/agent/utmstack_agent_service_arm64" -Destination "./dependencies/agent/" + Copy-Item -Path "${{ github.workspace }}/agent/utmstack_agent_service.exe" -Destination "./dependencies/agent/" + # Copy-Item -Path "${{ github.workspace }}/agent/utmstack_agent_service_arm64.exe" -Destination "./dependencies/agent/" + Copy-Item -Path "${{ github.workspace }}/agent/version.json" -Destination "./dependencies/agent/" + + docker build -t ghcr.io/utmstack/utmstack/agent-manager:${{ needs.setup_deployment.outputs.env_version }} . + docker push ghcr.io/utmstack/utmstack/agent-manager:${{ needs.setup_deployment.outputs.env_version }} + echo "Agent Manager image built and pushed" + runner_release: - name: Deployment for Release + name: Images deployment needs: setup_deployment - if: ${{ needs.setup_deployment.outputs.env_version == 'v10' }} + if: ${{ needs.setup_deployment.outputs.env_version != '' }} strategy: fail-fast: false matrix: - service: ['agent-manager', 'aws', 'backend', 'correlation', 'frontend', 'bitdefender', 'mutate', 'office365', 'log-auth-proxy', 'sophos', 'user-auditor', 'web-pdf'] + service: ['aws', 'backend', 'correlation', 'frontend', 'bitdefender', 'mutate', 'office365', 'log-auth-proxy', 'sophos', 'user-auditor', 'web-pdf'] uses: ./.github/workflows/used-runner.yml with: microservice: ${{ matrix.service }} diff --git a/.github/workflows/production-deployment.yml b/.github/workflows/production-deployment.yml index a37ef257b..653bdca86 100644 --- a/.github/workflows/production-deployment.yml +++ b/.github/workflows/production-deployment.yml @@ -22,10 +22,10 @@ jobs: if [[ "${{ github.event.inputs.version_tag }}" =~ ^v[0-9]+\.[0-9]+\.[0-9]+$ ]]; then echo "✅ Version tag format is correct." - if [[ "${ github.ref }" =~ ^refs/heads/main) ]]; then - echo "✅ Base branch ${ github.ref } is valid." + if [[ "${{ github.ref }}" =~ ^refs/heads/main) ]]; then + echo "✅ Base branch ${{ github.ref }} is valid." else - echo "⛔ ERROR: Base branch ${ github.ref } is not valid. It should be main." + echo "⛔ ERROR: Base branch ${{ github.ref }} is not valid. It should be main." exit 1 fi @@ -38,7 +38,7 @@ jobs: echo "✅ User ${{ github.actor }} is a member of the core-developers team." else echo "⛔ ERROR: User ${{ github.actor }} is not a member of the core-developers team." - exit 1 + exit 1 fi else @@ -47,7 +47,7 @@ jobs: fi deploy: - name: Deploy + name: Deploy to Production needs: validations uses: ./.github/workflows/build.yml with: @@ -55,9 +55,9 @@ jobs: event_processor_tag: ${{ github.event.inputs.event_processor_tag }} environment: prod ghcr_token: ${{ secrets.GITHUB_TOKEN }} - sign_cert: ${{ vars.SIGN_CERT }} - sign_key: ${{ secrets.SIGN_KEY }} - sign_container: ${{ secrets.SIGN_CONTAINER }} - env: - CM_AUTH: ${{ secrets.CM_AUTH_PROD }} + secrets: + AGENT_SECRET_PREFIX: ${{ secrets.AGENT_SECRET_PREFIX }} + SIGN_KEY: ${{ secrets.SIGN_KEY }} + SIGN_CONTAINER: ${{ secrets.SIGN_CONTAINER }} + CM_AUTH: ${{ secrets.CM_AUTH_ALPHA }} \ No newline at end of file diff --git a/.github/workflows/rc-deployment.yml b/.github/workflows/rc-deployment.yml index 908385706..8e2417fd0 100644 --- a/.github/workflows/rc-deployment.yml +++ b/.github/workflows/rc-deployment.yml @@ -22,10 +22,10 @@ jobs: if [[ "${{ github.event.inputs.version_tag }}" =~ ^v[0-9]+\.[0-9]+\.[0-9]+-rc\.[0-9]+$ ]]; then echo "✅ Version tag format is correct." - if [[ "${ github.ref }" =~ ^refs/heads/main) ]]; then - echo "✅ Base branch ${ github.ref } is valid." + if [[ "${{ github.ref }}" =~ ^refs/heads/main) ]]; then + echo "✅ Base branch ${{ github.ref }} is valid." else - echo "⛔ ERROR: Base branch ${ github.ref } is not valid. It should be main." + echo "⛔ ERROR: Base branch ${{ github.ref }} is not valid. It should be main." exit 1 fi @@ -38,7 +38,7 @@ jobs: echo "✅ User ${{ github.actor }} is a member of the core-developers team." else echo "⛔ ERROR: User ${{ github.actor }} is not a member of the core-developers team." - exit 1 + exit 1 fi else @@ -47,17 +47,16 @@ jobs: fi deploy: - name: Deploy + name: Deploy to RC needs: validations uses: ./.github/workflows/build.yml with: version_tag: ${{ github.event.inputs.version_tag }} event_processor_tag: ${{ github.event.inputs.event_processor_tag }} environment: rc - ghcr_token: ${{ secrets.GITHUB_TOKEN }} - sign_cert: ${{ vars.SIGN_CERT }} - sign_key: ${{ secrets.SIGN_KEY }} - sign_container: ${{ secrets.SIGN_CONTAINER }} - env: - CM_AUTH: ${{ secrets.CM_AUTH_RC }} + secrets: + AGENT_SECRET_PREFIX: ${{ secrets.AGENT_SECRET_PREFIX }} + SIGN_KEY: ${{ secrets.SIGN_KEY }} + SIGN_CONTAINER: ${{ secrets.SIGN_CONTAINER }} + CM_AUTH: ${{ secrets.CM_AUTH_ALPHA }} \ No newline at end of file diff --git a/.github/workflows/used-runner.yml b/.github/workflows/used-runner.yml index c79c2907c..0ad6744e9 100644 --- a/.github/workflows/used-runner.yml +++ b/.github/workflows/used-runner.yml @@ -22,7 +22,7 @@ jobs: id: get_tech run: | folder_changed="${{inputs.microservice}}" - if [[ "$folder_changed" == "agent-manager" || "$folder_changed" == "aws" || "$folder_changed" == "correlation" || "$folder_changed" == "bitdefender" || "$folder_changed" == "office365" || "$folder_changed" == "sophos" || "$folder_changed" == "log-auth-proxy" ]]; then + if [[ "$folder_changed" == "aws" || "$folder_changed" == "correlation" || "$folder_changed" == "bitdefender" || "$folder_changed" == "office365" || "$folder_changed" == "sophos" || "$folder_changed" == "log-auth-proxy" ]]; then tech="golang" elif [[ "$folder_changed" == "backend" ]]; then tech="java-11" diff --git a/CHANGELOG.md b/CHANGELOG.md index c5725c7c1..1992b0f16 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,7 +1,9 @@ -# UTMStack 10.6.2 Release Notes -## Bug Fixes -- Enhanced the Log Explorer UI to improve usability by refining the display of Refresh, Save Query, Load Query, and Add Filter actions for a more intuitive user experience.. +# UTMStack 10.6.3 Release Notes +## New Features and Improvements +- **Agent & Collector Dependencies**: agents and collectors now fetch their dependencies from the **agent-manager**, improving consistency and centralizing dependency management. -- Updating installer to address missing GeoIP index +- **Agent Installation**: improved the installation messages for the agent to provide clearer instructions during the setup process. -- Retag docker images to github registry +- **Agent Service Cleanup**: removed unnecessary services to streamline the system and reduce overhead. + +- **Error Recovery**: enhanced the agent's ability to recover from certain data streaming errors when interacting with the agent-manager, improving stability and fault tolerance. diff --git a/agent-manager/Dockerfile b/agent-manager/Dockerfile index 857bbc0a5..8435564ac 100644 --- a/agent-manager/Dockerfile +++ b/agent-manager/Dockerfile @@ -1,6 +1,8 @@ FROM ubuntu:22.04 COPY agent-manager /app/ +COPY ./dependencies/agent/ /dependencies/agent/ +COPY ./dependencies/collector/ /dependencies/collector/ # Install jq RUN apt-get update && \ @@ -19,6 +21,7 @@ RUN GRPCURL_VERSION=1.8.1 && \ # Expose the gRPC agent-manager port EXPOSE 50051 +EXPOSE 8080 # Set the health check HEALTHCHECK --interval=60s --timeout=5s --start-period=5s --retries=3 CMD grpcurl -insecure -plaintext -d '{"service": ""}' localhost:50051 grpc.health.v1.Health/Check | jq -e '.status == "SERVING"' || exit 1 diff --git a/agent-manager/auth/dependencies_interceptor.go b/agent-manager/auth/dependencies_interceptor.go new file mode 100644 index 000000000..b1bc2980c --- /dev/null +++ b/agent-manager/auth/dependencies_interceptor.go @@ -0,0 +1,45 @@ +package auth + +import ( + "net/http" + "strconv" + + "github.com/gin-gonic/gin" + "google.golang.org/grpc/metadata" +) + +func HTTPAuthInterceptor() gin.HandlerFunc { + return func(c *gin.Context) { + connectionKey := c.GetHeader("connection-key") + id := c.GetHeader("id") + key := c.GetHeader("key") + requestURL := c.Request.URL.Path + + if connectionKey == "" && id == "" && key == "" { + c.AbortWithStatusJSON(http.StatusBadRequest, gin.H{"error": "authentication is not provided"}) + return + } else if connectionKey != "" { + if err := authenticateRequest(metadata.New(map[string]string{"connection-key": connectionKey}), "connection-key"); err != nil { + c.AbortWithStatusJSON(http.StatusUnauthorized, gin.H{"error": "invalid connection key"}) + return + } + } else if id != "" && key != "" { + idInt, err := strconv.ParseUint(id, 10, 32) + if err != nil { + c.AbortWithStatusJSON(http.StatusBadRequest, gin.H{"error": "id is not valid"}) + return + } + + if err := checkKeyAuth(key, idInt, requestURL); err != nil { + c.AbortWithStatusJSON(http.StatusUnauthorized, gin.H{"error": "invalid key"}) + return + } + + } else { + c.AbortWithStatusJSON(http.StatusBadRequest, gin.H{"error": "invalid auth type"}) + return + } + + c.Next() + } +} diff --git a/agent-manager/auth/interceptor.go b/agent-manager/auth/interceptor.go index 1f7ea180f..18e9fc894 100644 --- a/agent-manager/auth/interceptor.go +++ b/agent-manager/auth/interceptor.go @@ -124,9 +124,9 @@ type AuthResponse struct { } func getAuthCache(method string) []AuthResponse { - if strings.Contains(method, "agent.AgentService") { + if strings.Contains(method, "agent.AgentService") || strings.Contains(method, "/dependencies/agent") { return convertMapToAuthResponses(agent.CacheAgent) - } else if strings.Contains(method, "agent.CollectorService") { + } else if strings.Contains(method, "agent.CollectorService") || strings.Contains(method, "/dependencies/collector") { return convertMapToAuthResponses(agent.CacheCollector) } else if strings.Contains(method, "agent.PingService") { return append(convertMapToAuthResponses(agent.CacheAgent), convertMapToAuthResponses(agent.CacheCollector)...) diff --git a/agent-manager/go.mod b/agent-manager/go.mod index 3a0689e92..a0822d381 100644 --- a/agent-manager/go.mod +++ b/agent-manager/go.mod @@ -6,26 +6,26 @@ toolchain go1.23.4 require ( github.com/AtlasInsideCorp/AtlasInsideAES v1.0.0 + github.com/gin-contrib/gzip v1.2.2 + github.com/gin-gonic/gin v1.10.0 github.com/google/uuid v1.6.0 - github.com/threatwinds/logger v1.1.12 - google.golang.org/grpc v1.70.0 + github.com/threatwinds/logger v1.2.1 + google.golang.org/grpc v1.71.0 google.golang.org/protobuf v1.36.5 gorm.io/driver/postgres v1.5.11 gorm.io/gorm v1.25.12 ) require ( - github.com/bytedance/sonic v1.12.1 // indirect - github.com/bytedance/sonic/loader v0.2.0 // indirect + github.com/bytedance/sonic v1.12.7 // indirect + github.com/bytedance/sonic/loader v0.2.2 // indirect github.com/cloudwego/base64x v0.1.4 // indirect - github.com/cloudwego/iasm v0.2.0 // indirect - github.com/gabriel-vasile/mimetype v1.4.5 // indirect - github.com/gin-contrib/sse v0.1.0 // indirect - github.com/gin-gonic/gin v1.10.0 // indirect + github.com/gabriel-vasile/mimetype v1.4.8 // indirect + github.com/gin-contrib/sse v1.0.0 // indirect github.com/go-playground/locales v0.14.1 // indirect github.com/go-playground/universal-translator v0.18.1 // indirect - github.com/go-playground/validator/v10 v10.22.0 // indirect - github.com/goccy/go-json v0.10.3 // indirect + github.com/go-playground/validator/v10 v10.24.0 // indirect + github.com/goccy/go-json v0.10.4 // indirect github.com/jackc/pgpassfile v1.0.0 // indirect github.com/jackc/pgservicefile v0.0.0-20221227161230-091c0ba34f0a // indirect github.com/jackc/pgx/v5 v5.5.5 // indirect @@ -33,21 +33,21 @@ require ( github.com/jinzhu/inflection v1.0.0 // indirect github.com/jinzhu/now v1.1.5 // indirect github.com/json-iterator/go v1.1.12 // indirect - github.com/klauspost/cpuid/v2 v2.2.8 // indirect + github.com/klauspost/cpuid/v2 v2.2.9 // indirect github.com/kr/text v0.2.0 // indirect github.com/leodido/go-urn v1.4.0 // indirect github.com/mattn/go-isatty v0.0.20 // indirect github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect github.com/modern-go/reflect2 v1.0.2 // indirect - github.com/pelletier/go-toml/v2 v2.2.2 // indirect + github.com/pelletier/go-toml/v2 v2.2.3 // indirect github.com/rogpeppe/go-internal v1.12.0 // indirect github.com/twitchyliquid64/golang-asm v0.15.1 // indirect github.com/ugorji/go/codec v1.2.12 // indirect - golang.org/x/arch v0.9.0 // indirect - golang.org/x/crypto v0.30.0 // indirect - golang.org/x/net v0.32.0 // indirect + golang.org/x/arch v0.13.0 // indirect + golang.org/x/crypto v0.32.0 // indirect + golang.org/x/net v0.34.0 // indirect golang.org/x/sync v0.10.0 // indirect - golang.org/x/sys v0.28.0 // indirect + golang.org/x/sys v0.29.0 // indirect golang.org/x/text v0.21.0 // indirect google.golang.org/genproto v0.0.0-20230110181048-76db0878b65f // indirect gopkg.in/natefinch/lumberjack.v2 v2.2.1 // indirect diff --git a/agent-manager/go.sum b/agent-manager/go.sum index 82e007443..852fb92da 100644 --- a/agent-manager/go.sum +++ b/agent-manager/go.sum @@ -1,22 +1,23 @@ github.com/AtlasInsideCorp/AtlasInsideAES v1.0.0 h1:TBiBl9KCa4i4epY0/q9WSC4ugavL6+6JUkOXWDnMM6I= github.com/AtlasInsideCorp/AtlasInsideAES v1.0.0/go.mod h1:cRhQ3TS/VEfu/z+qaciyuDZdtxgaXgaX8+G6Wa5NzBk= -github.com/bytedance/sonic v1.12.1 h1:jWl5Qz1fy7X1ioY74WqO0KjAMtAGQs4sYnjiEBiyX24= -github.com/bytedance/sonic v1.12.1/go.mod h1:B8Gt/XvtZ3Fqj+iSKMypzymZxw/FVwgIGKzMzT9r/rk= +github.com/bytedance/sonic v1.12.7 h1:CQU8pxOy9HToxhndH0Kx/S1qU/CuS9GnKYrGioDcU1Q= +github.com/bytedance/sonic v1.12.7/go.mod h1:tnbal4mxOMju17EGfknm2XyYcpyCnIROYOEYuemj13I= github.com/bytedance/sonic/loader v0.1.1/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= -github.com/bytedance/sonic/loader v0.2.0 h1:zNprn+lsIP06C/IqCHs3gPQIvnvpKbbxyXQP1iU4kWM= -github.com/bytedance/sonic/loader v0.2.0/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= +github.com/bytedance/sonic/loader v0.2.2 h1:jxAJuN9fOot/cyz5Q6dUuMJF5OqQ6+5GfA8FjjQ0R4o= +github.com/bytedance/sonic/loader v0.2.2/go.mod h1:N8A3vUdtUebEY2/VQC0MyhYeKUFosQU6FxH2JmUe6VI= github.com/cloudwego/base64x v0.1.4 h1:jwCgWpFanWmN8xoIUHa2rtzmkd5J2plF/dnLS6Xd/0Y= github.com/cloudwego/base64x v0.1.4/go.mod h1:0zlkT4Wn5C6NdauXdJRhSKRlJvmclQ1hhJgA0rcu/8w= -github.com/cloudwego/iasm v0.2.0 h1:1KNIy1I1H9hNNFEEH3DVnI4UujN+1zjpuk6gwHLTssg= github.com/cloudwego/iasm v0.2.0/go.mod h1:8rXZaNYT2n95jn+zTI1sDr+IgcD2GVs0nlbbQPiEFhY= github.com/creack/pty v1.1.9/go.mod h1:oKZEueFk5CKHvIhNR5MUki03XCEU+Q6VDXinZuGJ33E= github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/gabriel-vasile/mimetype v1.4.5 h1:J7wGKdGu33ocBOhGy0z653k/lFKLFDPJMG8Gql0kxn4= -github.com/gabriel-vasile/mimetype v1.4.5/go.mod h1:ibHel+/kbxn9x2407k1izTA1S81ku1z/DlgOW2QE0M4= -github.com/gin-contrib/sse v0.1.0 h1:Y/yl/+YNO8GZSjAhjMsSuLt29uWRFHdHYUb5lYOV9qE= -github.com/gin-contrib/sse v0.1.0/go.mod h1:RHrZQHXnP2xjPF+u1gW/2HnVO7nvIa9PG3Gm+fLHvGI= +github.com/gabriel-vasile/mimetype v1.4.8 h1:FfZ3gj38NjllZIeJAmMhr+qKL8Wu+nOoI3GqacKw1NM= +github.com/gabriel-vasile/mimetype v1.4.8/go.mod h1:ByKUIKGjh1ODkGM1asKUbQZOLGrPjydw3hYPU2YU9t8= +github.com/gin-contrib/gzip v1.2.2 h1:iUU/EYCM8ENfkjmZaVrxbjF/ZC267Iqv5S0MMCMEliI= +github.com/gin-contrib/gzip v1.2.2/go.mod h1:C1a5cacjlDsS20cKnHlZRCPUu57D3qH6B2pV0rl+Y/s= +github.com/gin-contrib/sse v1.0.0 h1:y3bT1mUWUxDpW4JLQg/HnTqV4rozuW4tC9eFKTxYI9E= +github.com/gin-contrib/sse v1.0.0/go.mod h1:zNuFdwarAygJBht0NTKiSi3jRf6RbqeILZ9Sp6Slhe0= github.com/gin-gonic/gin v1.10.0 h1:nTuyha1TYqgedzytsKYqna+DfLos46nTv2ygFy86HFU= github.com/gin-gonic/gin v1.10.0/go.mod h1:4PMNQiOhvDRa013RKVbsiNwoyezlm2rm0uX/T7kzp5Y= github.com/go-logr/logr v1.4.2 h1:6pFjapn8bFcIbiKo3XT4j/BhANplGihG6tvd+8rYgrY= @@ -29,10 +30,10 @@ github.com/go-playground/locales v0.14.1 h1:EWaQ/wswjilfKLTECiXz7Rh+3BjFhfDFKv/o github.com/go-playground/locales v0.14.1/go.mod h1:hxrqLVvrK65+Rwrd5Fc6F2O76J/NuW9t0sjnWqG1slY= github.com/go-playground/universal-translator v0.18.1 h1:Bcnm0ZwsGyWbCzImXv+pAJnYK9S473LQFuzCbDbfSFY= github.com/go-playground/universal-translator v0.18.1/go.mod h1:xekY+UJKNuX9WP91TpwSH2VMlDf28Uj24BCp08ZFTUY= -github.com/go-playground/validator/v10 v10.22.0 h1:k6HsTZ0sTnROkhS//R0O+55JgM8C4Bx7ia+JlgcnOao= -github.com/go-playground/validator/v10 v10.22.0/go.mod h1:dbuPbCMFw/DrkbEynArYaCwl3amGuJotoKCe95atGMM= -github.com/goccy/go-json v0.10.3 h1:KZ5WoDbxAIgm2HNbYckL0se1fHD6rz5j4ywS6ebzDqA= -github.com/goccy/go-json v0.10.3/go.mod h1:oq7eo15ShAhp70Anwd5lgX2pLfOS3QCiwU/PULtXL6M= +github.com/go-playground/validator/v10 v10.24.0 h1:KHQckvo8G6hlWnrPX4NJJ+aBfWNAE/HH+qdL2cBpCmg= +github.com/go-playground/validator/v10 v10.24.0/go.mod h1:GGzBIJMuE98Ic/kJsBXbz1x/7cByt++cQ+YOuDM5wus= +github.com/goccy/go-json v0.10.4 h1:JSwxQzIqKfmFX1swYPpUThQZp/Ka4wzJdK0LWVytLPM= +github.com/goccy/go-json v0.10.4/go.mod h1:oq7eo15ShAhp70Anwd5lgX2pLfOS3QCiwU/PULtXL6M= github.com/golang/protobuf v1.5.4 h1:i7eJL8qZTpSEXOPTxNKhASYpMn+8e5Q6AdndVa1dWek= github.com/golang/protobuf v1.5.4/go.mod h1:lnTiLA8Wa4RWRcIUkrtSVa5nRhsEGBg48fD6rSs7xps= github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI= @@ -55,8 +56,8 @@ github.com/jinzhu/now v1.1.5/go.mod h1:d3SSVoowX0Lcu0IBviAWJpolVfI5UJVZZ7cO71lE/ github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= -github.com/klauspost/cpuid/v2 v2.2.8 h1:+StwCXwm9PdpiEkPyzBXIy+M9KUb4ODm0Zarf1kS5BM= -github.com/klauspost/cpuid/v2 v2.2.8/go.mod h1:Lcz8mBdAVJIBVzewtcLocK12l3Y+JytZYpaMropDUws= +github.com/klauspost/cpuid/v2 v2.2.9 h1:66ze0taIn2H33fBvCkXuv9BmCwDfafmiIVpKV9kKGuY= +github.com/klauspost/cpuid/v2 v2.2.9/go.mod h1:rqkxqrZ1EhYM9G+hXH7YdowN5R5RGN6NK4QwQ3WMXF8= github.com/knz/go-libedit v1.10.1/go.mod h1:MZTVkCWyz0oBc7JOWP3wNAzd002ZbM/5hgShxwh4x8M= github.com/kr/pretty v0.3.0 h1:WgNl7dwNpEZ6jJ9k1snq4pZsg7DOEN8hP9Xw0Tsjwk0= github.com/kr/pretty v0.3.0/go.mod h1:640gp4NfQd8pI5XOwp5fnNeVWj67G7CFk/SaSQn7NBk= @@ -71,8 +72,8 @@ github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= -github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM= -github.com/pelletier/go-toml/v2 v2.2.2/go.mod h1:1t835xjRzz80PqgE6HHgN2JOsmgYu/h4qDAS4n929Rs= +github.com/pelletier/go-toml/v2 v2.2.3 h1:YmeHyLY8mFWbdkNWwpr+qIL2bEqT0o95WSdkNHvL12M= +github.com/pelletier/go-toml/v2 v2.2.3/go.mod h1:MfCQTFTvCcUyyvvwm1+G6H/jORL20Xlb6rzQu9GuUkc= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= github.com/rogpeppe/go-internal v1.12.0 h1:exVL4IDcn6na9z1rAb56Vxr+CgyK3nn3O+epU5NdKM8= @@ -87,42 +88,43 @@ github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/ github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU= github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o6fzry7u4= github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= -github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= -github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= +github.com/stretchr/testify v1.10.0 h1:Xv5erBjTwe/5IxqUQTdXv5kgmIvbHo3QQyRwhJsOfJA= +github.com/stretchr/testify v1.10.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= +github.com/threatwinds/logger v1.2.1 h1:uN7efZaHobMX3DRi6GOPtxESPxt5xj0bNflnmgklwII= +github.com/threatwinds/logger v1.2.1/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= github.com/ugorji/go/codec v1.2.12/go.mod h1:UNopzCgEMSXjBc6AOMqYvWC1ktqTAfzJZUZgYf6w6lg= -go.opentelemetry.io/otel v1.32.0 h1:WnBN+Xjcteh0zdk01SVqV55d/m62NJLJdIyb4y/WO5U= -go.opentelemetry.io/otel v1.32.0/go.mod h1:00DCVSB0RQcnzlwyTfqtxSm+DRr9hpYrHjNGiBHVQIg= -go.opentelemetry.io/otel/metric v1.32.0 h1:xV2umtmNcThh2/a/aCP+h64Xx5wsj8qqnkYZktzNa0M= -go.opentelemetry.io/otel/metric v1.32.0/go.mod h1:jH7CIbbK6SH2V2wE16W05BHCtIDzauciCRLoc/SyMv8= -go.opentelemetry.io/otel/sdk v1.32.0 h1:RNxepc9vK59A8XsgZQouW8ue8Gkb4jpWtJm9ge5lEG4= -go.opentelemetry.io/otel/sdk v1.32.0/go.mod h1:LqgegDBjKMmb2GC6/PrTnteJG39I8/vJCAP9LlJXEjU= -go.opentelemetry.io/otel/sdk/metric v1.32.0 h1:rZvFnvmvawYb0alrYkjraqJq0Z4ZUJAiyYCU9snn1CU= -go.opentelemetry.io/otel/sdk/metric v1.32.0/go.mod h1:PWeZlq0zt9YkYAp3gjKZ0eicRYvOh1Gd+X99x6GHpCQ= -go.opentelemetry.io/otel/trace v1.32.0 h1:WIC9mYrXf8TmY/EXuULKc8hR17vE+Hjv2cssQDe03fM= -go.opentelemetry.io/otel/trace v1.32.0/go.mod h1:+i4rkvCraA+tG6AzwloGaCtkx53Fa+L+V8e9a7YvhT8= -golang.org/x/arch v0.9.0 h1:ub9TgUInamJ8mrZIGlBG6/4TqWeMszd4N8lNorbrr6k= -golang.org/x/arch v0.9.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= -golang.org/x/crypto v0.30.0 h1:RwoQn3GkWiMkzlX562cLB7OxWvjH1L8xutO2WoJcRoY= -golang.org/x/crypto v0.30.0/go.mod h1:kDsLvtWBEx7MV9tJOj9bnXsPbxwJQ6csT/x4KIN4Ssk= -golang.org/x/net v0.32.0 h1:ZqPmj8Kzc+Y6e0+skZsuACbx+wzMgo5MQsJh9Qd6aYI= -golang.org/x/net v0.32.0/go.mod h1:CwU0IoeOlnQQWJ6ioyFrfRuomB8GKF6KbYXZVyeXNfs= +go.opentelemetry.io/auto/sdk v1.1.0 h1:cH53jehLUN6UFLY71z+NDOiNJqDdPRaXzTel0sJySYA= +go.opentelemetry.io/auto/sdk v1.1.0/go.mod h1:3wSPjt5PWp2RhlCcmmOial7AvC4DQqZb7a7wCow3W8A= +go.opentelemetry.io/otel v1.34.0 h1:zRLXxLCgL1WyKsPVrgbSdMN4c0FMkDAskSTQP+0hdUY= +go.opentelemetry.io/otel v1.34.0/go.mod h1:OWFPOQ+h4G8xpyjgqo4SxJYdDQ/qmRH+wivy7zzx9oI= +go.opentelemetry.io/otel/metric v1.34.0 h1:+eTR3U0MyfWjRDhmFMxe2SsW64QrZ84AOhvqS7Y+PoQ= +go.opentelemetry.io/otel/metric v1.34.0/go.mod h1:CEDrp0fy2D0MvkXE+dPV7cMi8tWZwX3dmaIhwPOaqHE= +go.opentelemetry.io/otel/sdk v1.34.0 h1:95zS4k/2GOy069d321O8jWgYsW3MzVV+KuSPKp7Wr1A= +go.opentelemetry.io/otel/sdk v1.34.0/go.mod h1:0e/pNiaMAqaykJGKbi+tSjWfNNHMTxoC9qANsCzbyxU= +go.opentelemetry.io/otel/sdk/metric v1.34.0 h1:5CeK9ujjbFVL5c1PhLuStg1wxA7vQv7ce1EK0Gyvahk= +go.opentelemetry.io/otel/sdk/metric v1.34.0/go.mod h1:jQ/r8Ze28zRKoNRdkjCZxfs6YvBTG1+YIqyFVFYec5w= +go.opentelemetry.io/otel/trace v1.34.0 h1:+ouXS2V8Rd4hp4580a8q23bg0azF2nI8cqLYnC8mh/k= +go.opentelemetry.io/otel/trace v1.34.0/go.mod h1:Svm7lSjQD7kG7KJ/MUHPVXSDGz2OX4h0M2jHBhmSfRE= +golang.org/x/arch v0.13.0 h1:KCkqVVV1kGg0X87TFysjCJ8MxtZEIU4Ja/yXGeoECdA= +golang.org/x/arch v0.13.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= +golang.org/x/crypto v0.32.0 h1:euUpcYgM8WcP71gNpTqQCn6rC2t6ULUPiOzfWaXVVfc= +golang.org/x/crypto v0.32.0/go.mod h1:ZnnJkOaASj8g0AjIduWNlq2NRxL0PlBrbKVyZ6V/Ugc= +golang.org/x/net v0.34.0 h1:Mb7Mrk043xzHgnRM88suvJFwzVrRfHEHJEl5/71CKw0= +golang.org/x/net v0.34.0/go.mod h1:di0qlW3YNM5oh6GqDGQr92MyTozJPmybPK4Ev/Gm31k= golang.org/x/sync v0.10.0 h1:3NQrjDixjgGwUOCaF8w2+VYHv0Ve/vGYSbdkTa98gmQ= golang.org/x/sync v0.10.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= -golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.28.0 h1:Fksou7UEQUWlKvIdsqzJmUmCX3cZuD2+P3XyyzwMhlA= -golang.org/x/sys v0.28.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= +golang.org/x/sys v0.29.0 h1:TPYlXGxvx1MGTn2GiZDhnjPA9wZzZeGKHHmKhHYvgaU= +golang.org/x/sys v0.29.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= golang.org/x/text v0.21.0 h1:zyQAAkrwaneQ066sspRyJaG9VNi/YJ1NfzcGB3hZ/qo= golang.org/x/text v0.21.0/go.mod h1:4IBbMaMmOPCJ8SecivzSH54+73PCFmPWxNTLm+vZkEQ= google.golang.org/genproto v0.0.0-20230110181048-76db0878b65f h1:BWUVssLB0HVOSY78gIdvk1dTVYtT1y8SBWtPYuTJ/6w= google.golang.org/genproto v0.0.0-20230110181048-76db0878b65f/go.mod h1:RGgjbofJ8xD9Sq1VVhDM1Vok1vRONV+rg+CjzG4SZKM= -google.golang.org/grpc v1.70.0 h1:pWFv03aZoHzlRKHWicjsZytKAiYCtNS0dHbXnIdq7jQ= -google.golang.org/grpc v1.70.0/go.mod h1:ofIJqVKDXx/JiXrwr2IG4/zwdH9txy3IlF40RmcJSQw= +google.golang.org/grpc v1.71.0 h1:kF77BGdPTQ4/JZWMlb9VpJ5pa25aqvVqogsxNHHdeBg= +google.golang.org/grpc v1.71.0/go.mod h1:H0GRtasmQOh9LkFoCPDu3ZrwUtD1YGE+b2vYBYd/8Ec= google.golang.org/protobuf v1.36.5 h1:tPhr+woSbjfYvY6/GPufUoYizxw1cF/yFoxJ2fmpwlM= google.golang.org/protobuf v1.36.5/go.mod h1:9fA7Ob0pmnwhb644+1+CVWFRbNajQ6iRojtC/QF5bRE= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= diff --git a/agent-manager/main.go b/agent-manager/main.go index 606b67a71..abb1281d4 100644 --- a/agent-manager/main.go +++ b/agent-manager/main.go @@ -11,6 +11,7 @@ import ( "github.com/utmstack/UTMStack/agent-manager/auth" "github.com/utmstack/UTMStack/agent-manager/config" "github.com/utmstack/UTMStack/agent-manager/migration" + "github.com/utmstack/UTMStack/agent-manager/updates" "github.com/utmstack/UTMStack/agent-manager/util" "google.golang.org/grpc" "google.golang.org/grpc/codes" @@ -74,6 +75,7 @@ func main() { // Set the health status to SERVING healthServer.SetServingStatus("", grpc_health_v1.HealthCheckResponse_SERVING) s.InitPingSync() + updates.InitUpdatesManager() // Start the gRPC server lis, err := net.Listen("tcp", "0.0.0.0:50051") diff --git a/agent-manager/updates/updates.go b/agent-manager/updates/updates.go new file mode 100644 index 000000000..9d8369fc4 --- /dev/null +++ b/agent-manager/updates/updates.go @@ -0,0 +1,42 @@ +package updates + +import ( + "net/http" + + "github.com/gin-contrib/gzip" + "github.com/gin-gonic/gin" + "github.com/utmstack/UTMStack/agent-manager/auth" + "github.com/utmstack/UTMStack/agent-manager/util" +) + +type Version struct { + Version string `json:"version"` +} + +func InitUpdatesManager() { + go ServeDependencies() +} + +func ServeDependencies() { + gin.SetMode(gin.ReleaseMode) + r := gin.New() + r.Use( + gin.Recovery(), + gzip.Gzip(gzip.DefaultCompression), + ) + + r.NoRoute(notFound) + + group := r.Group("/private", auth.HTTPAuthInterceptor()) + group.StaticFS("/dependencies", http.Dir("/dependencies")) + + util.GetLogger().Info("Starting HTTP server on port 8080") + if err := r.RunTLS(":8080", "/cert/utm.crt", "/cert/utm.key"); err != nil { + util.GetLogger().ErrorF("error starting HTTP server: %v", err) + return + } +} + +func notFound(c *gin.Context) { + c.JSON(http.StatusNotFound, gin.H{"error": "not found"}) +} diff --git a/agent-manager/util/files.go b/agent-manager/util/files.go new file mode 100644 index 000000000..c4530ea4d --- /dev/null +++ b/agent-manager/util/files.go @@ -0,0 +1,18 @@ +package util + +import ( + "encoding/json" + "os" +) + +func ReadJson(fileName string, data interface{}) error { + content, err := os.ReadFile(fileName) + if err != nil { + return err + } + err = json.Unmarshal(content, data) + if err != nil { + return err + } + return nil +} diff --git a/agent/agent/README.md b/agent/README.md similarity index 100% rename from agent/agent/README.md rename to agent/README.md diff --git a/agent/agent/agent/agent.pb.go b/agent/agent/agent.pb.go similarity index 100% rename from agent/agent/agent/agent.pb.go rename to agent/agent/agent.pb.go diff --git a/agent/agent/agent/agent_config.pb.go b/agent/agent/agent/agent_config.pb.go deleted file mode 100644 index de13d7db6..000000000 --- a/agent/agent/agent/agent_config.pb.go +++ /dev/null @@ -1,666 +0,0 @@ -// Code generated by protoc-gen-go. DO NOT EDIT. -// versions: -// protoc-gen-go v1.28.1 -// protoc v3.21.12 -// source: agent_config.proto - -package agent - -import ( - protoreflect "google.golang.org/protobuf/reflect/protoreflect" - protoimpl "google.golang.org/protobuf/runtime/protoimpl" - reflect "reflect" - sync "sync" -) - -const ( - // Verify that this generated code is sufficiently up-to-date. - _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion) - // Verify that runtime/protoimpl is sufficiently up-to-date. - _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20) -) - -type AgentModule struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Id uint32 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"` - AgentId uint32 `protobuf:"varint,2,opt,name=agent_id,json=agentId,proto3" json:"agent_id,omitempty"` - ShortName string `protobuf:"bytes,3,opt,name=short_name,json=shortName,proto3" json:"short_name,omitempty"` - LargeName string `protobuf:"bytes,4,opt,name=large_name,json=largeName,proto3" json:"large_name,omitempty"` - Description string `protobuf:"bytes,5,opt,name=description,proto3" json:"description,omitempty"` - Enabled bool `protobuf:"varint,6,opt,name=enabled,proto3" json:"enabled,omitempty"` - AllowDisabled bool `protobuf:"varint,7,opt,name=allow_disabled,json=allowDisabled,proto3" json:"allow_disabled,omitempty"` - ModuleConfigs []*AgentModuleConfiguration `protobuf:"bytes,8,rep,name=module_configs,json=moduleConfigs,proto3" json:"module_configs,omitempty"` -} - -func (x *AgentModule) Reset() { - *x = AgentModule{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_config_proto_msgTypes[0] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *AgentModule) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*AgentModule) ProtoMessage() {} - -func (x *AgentModule) ProtoReflect() protoreflect.Message { - mi := &file_agent_config_proto_msgTypes[0] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use AgentModule.ProtoReflect.Descriptor instead. -func (*AgentModule) Descriptor() ([]byte, []int) { - return file_agent_config_proto_rawDescGZIP(), []int{0} -} - -func (x *AgentModule) GetId() uint32 { - if x != nil { - return x.Id - } - return 0 -} - -func (x *AgentModule) GetAgentId() uint32 { - if x != nil { - return x.AgentId - } - return 0 -} - -func (x *AgentModule) GetShortName() string { - if x != nil { - return x.ShortName - } - return "" -} - -func (x *AgentModule) GetLargeName() string { - if x != nil { - return x.LargeName - } - return "" -} - -func (x *AgentModule) GetDescription() string { - if x != nil { - return x.Description - } - return "" -} - -func (x *AgentModule) GetEnabled() bool { - if x != nil { - return x.Enabled - } - return false -} - -func (x *AgentModule) GetAllowDisabled() bool { - if x != nil { - return x.AllowDisabled - } - return false -} - -func (x *AgentModule) GetModuleConfigs() []*AgentModuleConfiguration { - if x != nil { - return x.ModuleConfigs - } - return nil -} - -type UpdateAgentModule struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - AgentModuleShort string `protobuf:"bytes,1,opt,name=agent_module_short,json=agentModuleShort,proto3" json:"agent_module_short,omitempty"` - ConfKey string `protobuf:"bytes,4,opt,name=conf_key,json=confKey,proto3" json:"conf_key,omitempty"` - ConfValue string `protobuf:"bytes,5,opt,name=conf_value,json=confValue,proto3" json:"conf_value,omitempty"` -} - -func (x *UpdateAgentModule) Reset() { - *x = UpdateAgentModule{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_config_proto_msgTypes[1] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *UpdateAgentModule) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*UpdateAgentModule) ProtoMessage() {} - -func (x *UpdateAgentModule) ProtoReflect() protoreflect.Message { - mi := &file_agent_config_proto_msgTypes[1] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use UpdateAgentModule.ProtoReflect.Descriptor instead. -func (*UpdateAgentModule) Descriptor() ([]byte, []int) { - return file_agent_config_proto_rawDescGZIP(), []int{1} -} - -func (x *UpdateAgentModule) GetAgentModuleShort() string { - if x != nil { - return x.AgentModuleShort - } - return "" -} - -func (x *UpdateAgentModule) GetConfKey() string { - if x != nil { - return x.ConfKey - } - return "" -} - -func (x *UpdateAgentModule) GetConfValue() string { - if x != nil { - return x.ConfValue - } - return "" -} - -type AgentModuleConfiguration struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Id uint32 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"` - AgentModuleId uint32 `protobuf:"varint,2,opt,name=agent_module_id,json=agentModuleId,proto3" json:"agent_module_id,omitempty"` - ShortName string `protobuf:"bytes,3,opt,name=short_name,json=shortName,proto3" json:"short_name,omitempty"` - ConfKey string `protobuf:"bytes,4,opt,name=conf_key,json=confKey,proto3" json:"conf_key,omitempty"` - ConfValue string `protobuf:"bytes,5,opt,name=conf_value,json=confValue,proto3" json:"conf_value,omitempty"` - ConfName string `protobuf:"bytes,6,opt,name=conf_name,json=confName,proto3" json:"conf_name,omitempty"` - ConfDescription string `protobuf:"bytes,7,opt,name=conf_description,json=confDescription,proto3" json:"conf_description,omitempty"` - ConfDatatype string `protobuf:"bytes,8,opt,name=conf_datatype,json=confDatatype,proto3" json:"conf_datatype,omitempty"` - ConfRequired bool `protobuf:"varint,9,opt,name=conf_required,json=confRequired,proto3" json:"conf_required,omitempty"` - ConfRegex string `protobuf:"bytes,10,opt,name=conf_regex,json=confRegex,proto3" json:"conf_regex,omitempty"` -} - -func (x *AgentModuleConfiguration) Reset() { - *x = AgentModuleConfiguration{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_config_proto_msgTypes[2] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *AgentModuleConfiguration) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*AgentModuleConfiguration) ProtoMessage() {} - -func (x *AgentModuleConfiguration) ProtoReflect() protoreflect.Message { - mi := &file_agent_config_proto_msgTypes[2] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use AgentModuleConfiguration.ProtoReflect.Descriptor instead. -func (*AgentModuleConfiguration) Descriptor() ([]byte, []int) { - return file_agent_config_proto_rawDescGZIP(), []int{2} -} - -func (x *AgentModuleConfiguration) GetId() uint32 { - if x != nil { - return x.Id - } - return 0 -} - -func (x *AgentModuleConfiguration) GetAgentModuleId() uint32 { - if x != nil { - return x.AgentModuleId - } - return 0 -} - -func (x *AgentModuleConfiguration) GetShortName() string { - if x != nil { - return x.ShortName - } - return "" -} - -func (x *AgentModuleConfiguration) GetConfKey() string { - if x != nil { - return x.ConfKey - } - return "" -} - -func (x *AgentModuleConfiguration) GetConfValue() string { - if x != nil { - return x.ConfValue - } - return "" -} - -func (x *AgentModuleConfiguration) GetConfName() string { - if x != nil { - return x.ConfName - } - return "" -} - -func (x *AgentModuleConfiguration) GetConfDescription() string { - if x != nil { - return x.ConfDescription - } - return "" -} - -func (x *AgentModuleConfiguration) GetConfDatatype() string { - if x != nil { - return x.ConfDatatype - } - return "" -} - -func (x *AgentModuleConfiguration) GetConfRequired() bool { - if x != nil { - return x.ConfRequired - } - return false -} - -func (x *AgentModuleConfiguration) GetConfRegex() string { - if x != nil { - return x.ConfRegex - } - return "" -} - -type UpdateConfigResponse struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Accepted string `protobuf:"bytes,1,opt,name=accepted,proto3" json:"accepted,omitempty"` -} - -func (x *UpdateConfigResponse) Reset() { - *x = UpdateConfigResponse{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_config_proto_msgTypes[3] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *UpdateConfigResponse) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*UpdateConfigResponse) ProtoMessage() {} - -func (x *UpdateConfigResponse) ProtoReflect() protoreflect.Message { - mi := &file_agent_config_proto_msgTypes[3] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use UpdateConfigResponse.ProtoReflect.Descriptor instead. -func (*UpdateConfigResponse) Descriptor() ([]byte, []int) { - return file_agent_config_proto_rawDescGZIP(), []int{3} -} - -func (x *UpdateConfigResponse) GetAccepted() string { - if x != nil { - return x.Accepted - } - return "" -} - -// ListAgentsRequest message definition -type ListAgentsModulesRequest struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - AgentKey string `protobuf:"bytes,2,opt,name=agent_key,json=agentKey,proto3" json:"agent_key,omitempty"` -} - -func (x *ListAgentsModulesRequest) Reset() { - *x = ListAgentsModulesRequest{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_config_proto_msgTypes[4] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *ListAgentsModulesRequest) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*ListAgentsModulesRequest) ProtoMessage() {} - -func (x *ListAgentsModulesRequest) ProtoReflect() protoreflect.Message { - mi := &file_agent_config_proto_msgTypes[4] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use ListAgentsModulesRequest.ProtoReflect.Descriptor instead. -func (*ListAgentsModulesRequest) Descriptor() ([]byte, []int) { - return file_agent_config_proto_rawDescGZIP(), []int{4} -} - -func (x *ListAgentsModulesRequest) GetAgentKey() string { - if x != nil { - return x.AgentKey - } - return "" -} - -// ListAgentsResponse message definition -type ListAgentsModulesResponse struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Modules []*AgentModule `protobuf:"bytes,1,rep,name=modules,proto3" json:"modules,omitempty"` -} - -func (x *ListAgentsModulesResponse) Reset() { - *x = ListAgentsModulesResponse{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_config_proto_msgTypes[5] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *ListAgentsModulesResponse) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*ListAgentsModulesResponse) ProtoMessage() {} - -func (x *ListAgentsModulesResponse) ProtoReflect() protoreflect.Message { - mi := &file_agent_config_proto_msgTypes[5] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use ListAgentsModulesResponse.ProtoReflect.Descriptor instead. -func (*ListAgentsModulesResponse) Descriptor() ([]byte, []int) { - return file_agent_config_proto_rawDescGZIP(), []int{5} -} - -func (x *ListAgentsModulesResponse) GetModules() []*AgentModule { - if x != nil { - return x.Modules - } - return nil -} - -var File_agent_config_proto protoreflect.FileDescriptor - -var file_agent_config_proto_rawDesc = []byte{ - 0x0a, 0x12, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x2e, 0x70, - 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x05, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x22, 0xa1, 0x02, 0x0a, 0x0b, - 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x12, 0x0e, 0x0a, 0x02, 0x69, - 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x0d, 0x52, 0x02, 0x69, 0x64, 0x12, 0x19, 0x0a, 0x08, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x5f, 0x69, 0x64, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0d, 0x52, 0x07, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x49, 0x64, 0x12, 0x1d, 0x0a, 0x0a, 0x73, 0x68, 0x6f, 0x72, 0x74, 0x5f, - 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x73, 0x68, 0x6f, 0x72, - 0x74, 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x1d, 0x0a, 0x0a, 0x6c, 0x61, 0x72, 0x67, 0x65, 0x5f, 0x6e, - 0x61, 0x6d, 0x65, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x6c, 0x61, 0x72, 0x67, 0x65, - 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, - 0x69, 0x6f, 0x6e, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, - 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x18, 0x0a, 0x07, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, - 0x64, 0x18, 0x06, 0x20, 0x01, 0x28, 0x08, 0x52, 0x07, 0x65, 0x6e, 0x61, 0x62, 0x6c, 0x65, 0x64, - 0x12, 0x25, 0x0a, 0x0e, 0x61, 0x6c, 0x6c, 0x6f, 0x77, 0x5f, 0x64, 0x69, 0x73, 0x61, 0x62, 0x6c, - 0x65, 0x64, 0x18, 0x07, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0d, 0x61, 0x6c, 0x6c, 0x6f, 0x77, 0x44, - 0x69, 0x73, 0x61, 0x62, 0x6c, 0x65, 0x64, 0x12, 0x46, 0x0a, 0x0e, 0x6d, 0x6f, 0x64, 0x75, 0x6c, - 0x65, 0x5f, 0x63, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x73, 0x18, 0x08, 0x20, 0x03, 0x28, 0x0b, 0x32, - 0x1f, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x6f, 0x64, - 0x75, 0x6c, 0x65, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x75, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, - 0x52, 0x0d, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x73, 0x22, - 0x7b, 0x0a, 0x11, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x6f, - 0x64, 0x75, 0x6c, 0x65, 0x12, 0x2c, 0x0a, 0x12, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x5f, 0x6d, 0x6f, - 0x64, 0x75, 0x6c, 0x65, 0x5f, 0x73, 0x68, 0x6f, 0x72, 0x74, 0x18, 0x01, 0x20, 0x01, 0x28, 0x09, - 0x52, 0x10, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x53, 0x68, 0x6f, - 0x72, 0x74, 0x12, 0x19, 0x0a, 0x08, 0x63, 0x6f, 0x6e, 0x66, 0x5f, 0x6b, 0x65, 0x79, 0x18, 0x04, - 0x20, 0x01, 0x28, 0x09, 0x52, 0x07, 0x63, 0x6f, 0x6e, 0x66, 0x4b, 0x65, 0x79, 0x12, 0x1d, 0x0a, - 0x0a, 0x63, 0x6f, 0x6e, 0x66, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x09, 0x63, 0x6f, 0x6e, 0x66, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x22, 0xdc, 0x02, 0x0a, - 0x18, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x43, 0x6f, 0x6e, 0x66, - 0x69, 0x67, 0x75, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, - 0x01, 0x20, 0x01, 0x28, 0x0d, 0x52, 0x02, 0x69, 0x64, 0x12, 0x26, 0x0a, 0x0f, 0x61, 0x67, 0x65, - 0x6e, 0x74, 0x5f, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x5f, 0x69, 0x64, 0x18, 0x02, 0x20, 0x01, - 0x28, 0x0d, 0x52, 0x0d, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x49, - 0x64, 0x12, 0x1d, 0x0a, 0x0a, 0x73, 0x68, 0x6f, 0x72, 0x74, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x18, - 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x73, 0x68, 0x6f, 0x72, 0x74, 0x4e, 0x61, 0x6d, 0x65, - 0x12, 0x19, 0x0a, 0x08, 0x63, 0x6f, 0x6e, 0x66, 0x5f, 0x6b, 0x65, 0x79, 0x18, 0x04, 0x20, 0x01, - 0x28, 0x09, 0x52, 0x07, 0x63, 0x6f, 0x6e, 0x66, 0x4b, 0x65, 0x79, 0x12, 0x1d, 0x0a, 0x0a, 0x63, - 0x6f, 0x6e, 0x66, 0x5f, 0x76, 0x61, 0x6c, 0x75, 0x65, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, - 0x09, 0x63, 0x6f, 0x6e, 0x66, 0x56, 0x61, 0x6c, 0x75, 0x65, 0x12, 0x1b, 0x0a, 0x09, 0x63, 0x6f, - 0x6e, 0x66, 0x5f, 0x6e, 0x61, 0x6d, 0x65, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x63, - 0x6f, 0x6e, 0x66, 0x4e, 0x61, 0x6d, 0x65, 0x12, 0x29, 0x0a, 0x10, 0x63, 0x6f, 0x6e, 0x66, 0x5f, - 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x07, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x0f, 0x63, 0x6f, 0x6e, 0x66, 0x44, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, - 0x6f, 0x6e, 0x12, 0x23, 0x0a, 0x0d, 0x63, 0x6f, 0x6e, 0x66, 0x5f, 0x64, 0x61, 0x74, 0x61, 0x74, - 0x79, 0x70, 0x65, 0x18, 0x08, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0c, 0x63, 0x6f, 0x6e, 0x66, 0x44, - 0x61, 0x74, 0x61, 0x74, 0x79, 0x70, 0x65, 0x12, 0x23, 0x0a, 0x0d, 0x63, 0x6f, 0x6e, 0x66, 0x5f, - 0x72, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, 0x64, 0x18, 0x09, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0c, - 0x63, 0x6f, 0x6e, 0x66, 0x52, 0x65, 0x71, 0x75, 0x69, 0x72, 0x65, 0x64, 0x12, 0x1d, 0x0a, 0x0a, - 0x63, 0x6f, 0x6e, 0x66, 0x5f, 0x72, 0x65, 0x67, 0x65, 0x78, 0x18, 0x0a, 0x20, 0x01, 0x28, 0x09, - 0x52, 0x09, 0x63, 0x6f, 0x6e, 0x66, 0x52, 0x65, 0x67, 0x65, 0x78, 0x22, 0x32, 0x0a, 0x14, 0x55, - 0x70, 0x64, 0x61, 0x74, 0x65, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x52, 0x65, 0x73, 0x70, 0x6f, - 0x6e, 0x73, 0x65, 0x12, 0x1a, 0x0a, 0x08, 0x61, 0x63, 0x63, 0x65, 0x70, 0x74, 0x65, 0x64, 0x18, - 0x01, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, 0x61, 0x63, 0x63, 0x65, 0x70, 0x74, 0x65, 0x64, 0x22, - 0x37, 0x0a, 0x18, 0x4c, 0x69, 0x73, 0x74, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x73, 0x4d, 0x6f, 0x64, - 0x75, 0x6c, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x1b, 0x0a, 0x09, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x5f, 0x6b, 0x65, 0x79, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x08, - 0x61, 0x67, 0x65, 0x6e, 0x74, 0x4b, 0x65, 0x79, 0x22, 0x49, 0x0a, 0x19, 0x4c, 0x69, 0x73, 0x74, - 0x41, 0x67, 0x65, 0x6e, 0x74, 0x73, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x52, 0x65, 0x73, - 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x2c, 0x0a, 0x07, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, - 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x12, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x41, - 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x52, 0x07, 0x6d, 0x6f, 0x64, 0x75, - 0x6c, 0x65, 0x73, 0x32, 0xca, 0x01, 0x0a, 0x12, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x43, 0x6f, 0x6e, - 0x66, 0x69, 0x67, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, 0x12, 0x55, 0x0a, 0x0e, 0x47, 0x65, - 0x74, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x12, 0x1f, 0x2e, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x73, 0x4d, - 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, 0x20, 0x2e, - 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x73, - 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x73, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, - 0x00, 0x12, 0x5d, 0x0a, 0x17, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, - 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x53, 0x74, 0x72, 0x65, 0x61, 0x6d, 0x12, 0x1f, 0x2e, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, - 0x43, 0x6f, 0x6e, 0x66, 0x69, 0x67, 0x75, 0x72, 0x61, 0x74, 0x69, 0x6f, 0x6e, 0x1a, 0x1b, 0x2e, - 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x55, 0x70, 0x64, 0x61, 0x74, 0x65, 0x43, 0x6f, 0x6e, 0x66, - 0x69, 0x67, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x22, 0x00, 0x28, 0x01, 0x30, 0x01, - 0x42, 0x32, 0x5a, 0x30, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, 0x6f, 0x6d, 0x2f, 0x75, - 0x74, 0x6d, 0x73, 0x74, 0x61, 0x63, 0x6b, 0x2f, 0x55, 0x54, 0x4d, 0x53, 0x74, 0x61, 0x63, 0x6b, - 0x2f, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2d, 0x6d, 0x61, 0x6e, 0x61, 0x67, 0x65, 0x72, 0x2f, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, -} - -var ( - file_agent_config_proto_rawDescOnce sync.Once - file_agent_config_proto_rawDescData = file_agent_config_proto_rawDesc -) - -func file_agent_config_proto_rawDescGZIP() []byte { - file_agent_config_proto_rawDescOnce.Do(func() { - file_agent_config_proto_rawDescData = protoimpl.X.CompressGZIP(file_agent_config_proto_rawDescData) - }) - return file_agent_config_proto_rawDescData -} - -var file_agent_config_proto_msgTypes = make([]protoimpl.MessageInfo, 6) -var file_agent_config_proto_goTypes = []interface{}{ - (*AgentModule)(nil), // 0: agent.AgentModule - (*UpdateAgentModule)(nil), // 1: agent.UpdateAgentModule - (*AgentModuleConfiguration)(nil), // 2: agent.AgentModuleConfiguration - (*UpdateConfigResponse)(nil), // 3: agent.UpdateConfigResponse - (*ListAgentsModulesRequest)(nil), // 4: agent.ListAgentsModulesRequest - (*ListAgentsModulesResponse)(nil), // 5: agent.ListAgentsModulesResponse -} -var file_agent_config_proto_depIdxs = []int32{ - 2, // 0: agent.AgentModule.module_configs:type_name -> agent.AgentModuleConfiguration - 0, // 1: agent.ListAgentsModulesResponse.modules:type_name -> agent.AgentModule - 4, // 2: agent.AgentConfigService.GetAgentConfig:input_type -> agent.ListAgentsModulesRequest - 2, // 3: agent.AgentConfigService.AgentModuleUpdateStream:input_type -> agent.AgentModuleConfiguration - 5, // 4: agent.AgentConfigService.GetAgentConfig:output_type -> agent.ListAgentsModulesResponse - 3, // 5: agent.AgentConfigService.AgentModuleUpdateStream:output_type -> agent.UpdateConfigResponse - 4, // [4:6] is the sub-list for method output_type - 2, // [2:4] is the sub-list for method input_type - 2, // [2:2] is the sub-list for extension type_name - 2, // [2:2] is the sub-list for extension extendee - 0, // [0:2] is the sub-list for field type_name -} - -func init() { file_agent_config_proto_init() } -func file_agent_config_proto_init() { - if File_agent_config_proto != nil { - return - } - if !protoimpl.UnsafeEnabled { - file_agent_config_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*AgentModule); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_config_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*UpdateAgentModule); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_config_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*AgentModuleConfiguration); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_config_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*UpdateConfigResponse); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_config_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ListAgentsModulesRequest); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_config_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ListAgentsModulesResponse); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - } - type x struct{} - out := protoimpl.TypeBuilder{ - File: protoimpl.DescBuilder{ - GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_agent_config_proto_rawDesc, - NumEnums: 0, - NumMessages: 6, - NumExtensions: 0, - NumServices: 1, - }, - GoTypes: file_agent_config_proto_goTypes, - DependencyIndexes: file_agent_config_proto_depIdxs, - MessageInfos: file_agent_config_proto_msgTypes, - }.Build() - File_agent_config_proto = out.File - file_agent_config_proto_rawDesc = nil - file_agent_config_proto_goTypes = nil - file_agent_config_proto_depIdxs = nil -} diff --git a/agent/agent/agent/agent_config_grpc.pb.go b/agent/agent/agent/agent_config_grpc.pb.go deleted file mode 100644 index 29d3b5235..000000000 --- a/agent/agent/agent/agent_config_grpc.pb.go +++ /dev/null @@ -1,154 +0,0 @@ -// Code generated by protoc-gen-go-grpc. DO NOT EDIT. -// versions: -// - protoc-gen-go-grpc v1.5.1 -// - protoc v3.21.12 -// source: agent_config.proto - -package agent - -import ( - context "context" - grpc "google.golang.org/grpc" - codes "google.golang.org/grpc/codes" - status "google.golang.org/grpc/status" -) - -// This is a compile-time assertion to ensure that this generated file -// is compatible with the grpc package it is being compiled against. -// Requires gRPC-Go v1.64.0 or later. -const _ = grpc.SupportPackageIsVersion9 - -const ( - AgentConfigService_GetAgentConfig_FullMethodName = "/agent.AgentConfigService/GetAgentConfig" - AgentConfigService_AgentModuleUpdateStream_FullMethodName = "/agent.AgentConfigService/AgentModuleUpdateStream" -) - -// AgentConfigServiceClient is the client API for AgentConfigService service. -// -// For semantics around ctx use and closing/ending streaming RPCs, please refer to https://pkg.go.dev/google.golang.org/grpc/?tab=doc#ClientConn.NewStream. -type AgentConfigServiceClient interface { - GetAgentConfig(ctx context.Context, in *ListAgentsModulesRequest, opts ...grpc.CallOption) (*ListAgentsModulesResponse, error) - AgentModuleUpdateStream(ctx context.Context, opts ...grpc.CallOption) (grpc.BidiStreamingClient[AgentModuleConfiguration, UpdateConfigResponse], error) -} - -type agentConfigServiceClient struct { - cc grpc.ClientConnInterface -} - -func NewAgentConfigServiceClient(cc grpc.ClientConnInterface) AgentConfigServiceClient { - return &agentConfigServiceClient{cc} -} - -func (c *agentConfigServiceClient) GetAgentConfig(ctx context.Context, in *ListAgentsModulesRequest, opts ...grpc.CallOption) (*ListAgentsModulesResponse, error) { - cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) - out := new(ListAgentsModulesResponse) - err := c.cc.Invoke(ctx, AgentConfigService_GetAgentConfig_FullMethodName, in, out, cOpts...) - if err != nil { - return nil, err - } - return out, nil -} - -func (c *agentConfigServiceClient) AgentModuleUpdateStream(ctx context.Context, opts ...grpc.CallOption) (grpc.BidiStreamingClient[AgentModuleConfiguration, UpdateConfigResponse], error) { - cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) - stream, err := c.cc.NewStream(ctx, &AgentConfigService_ServiceDesc.Streams[0], AgentConfigService_AgentModuleUpdateStream_FullMethodName, cOpts...) - if err != nil { - return nil, err - } - x := &grpc.GenericClientStream[AgentModuleConfiguration, UpdateConfigResponse]{ClientStream: stream} - return x, nil -} - -// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name. -type AgentConfigService_AgentModuleUpdateStreamClient = grpc.BidiStreamingClient[AgentModuleConfiguration, UpdateConfigResponse] - -// AgentConfigServiceServer is the server API for AgentConfigService service. -// All implementations must embed UnimplementedAgentConfigServiceServer -// for forward compatibility. -type AgentConfigServiceServer interface { - GetAgentConfig(context.Context, *ListAgentsModulesRequest) (*ListAgentsModulesResponse, error) - AgentModuleUpdateStream(grpc.BidiStreamingServer[AgentModuleConfiguration, UpdateConfigResponse]) error - mustEmbedUnimplementedAgentConfigServiceServer() -} - -// UnimplementedAgentConfigServiceServer must be embedded to have -// forward compatible implementations. -// -// NOTE: this should be embedded by value instead of pointer to avoid a nil -// pointer dereference when methods are called. -type UnimplementedAgentConfigServiceServer struct{} - -func (UnimplementedAgentConfigServiceServer) GetAgentConfig(context.Context, *ListAgentsModulesRequest) (*ListAgentsModulesResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method GetAgentConfig not implemented") -} -func (UnimplementedAgentConfigServiceServer) AgentModuleUpdateStream(grpc.BidiStreamingServer[AgentModuleConfiguration, UpdateConfigResponse]) error { - return status.Errorf(codes.Unimplemented, "method AgentModuleUpdateStream not implemented") -} -func (UnimplementedAgentConfigServiceServer) mustEmbedUnimplementedAgentConfigServiceServer() {} -func (UnimplementedAgentConfigServiceServer) testEmbeddedByValue() {} - -// UnsafeAgentConfigServiceServer may be embedded to opt out of forward compatibility for this service. -// Use of this interface is not recommended, as added methods to AgentConfigServiceServer will -// result in compilation errors. -type UnsafeAgentConfigServiceServer interface { - mustEmbedUnimplementedAgentConfigServiceServer() -} - -func RegisterAgentConfigServiceServer(s grpc.ServiceRegistrar, srv AgentConfigServiceServer) { - // If the following call pancis, it indicates UnimplementedAgentConfigServiceServer was - // embedded by pointer and is nil. This will cause panics if an - // unimplemented method is ever invoked, so we test this at initialization - // time to prevent it from happening at runtime later due to I/O. - if t, ok := srv.(interface{ testEmbeddedByValue() }); ok { - t.testEmbeddedByValue() - } - s.RegisterService(&AgentConfigService_ServiceDesc, srv) -} - -func _AgentConfigService_GetAgentConfig_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(ListAgentsModulesRequest) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(AgentConfigServiceServer).GetAgentConfig(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: AgentConfigService_GetAgentConfig_FullMethodName, - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(AgentConfigServiceServer).GetAgentConfig(ctx, req.(*ListAgentsModulesRequest)) - } - return interceptor(ctx, in, info, handler) -} - -func _AgentConfigService_AgentModuleUpdateStream_Handler(srv interface{}, stream grpc.ServerStream) error { - return srv.(AgentConfigServiceServer).AgentModuleUpdateStream(&grpc.GenericServerStream[AgentModuleConfiguration, UpdateConfigResponse]{ServerStream: stream}) -} - -// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name. -type AgentConfigService_AgentModuleUpdateStreamServer = grpc.BidiStreamingServer[AgentModuleConfiguration, UpdateConfigResponse] - -// AgentConfigService_ServiceDesc is the grpc.ServiceDesc for AgentConfigService service. -// It's only intended for direct use with grpc.RegisterService, -// and not to be introspected or modified (even as a copy) -var AgentConfigService_ServiceDesc = grpc.ServiceDesc{ - ServiceName: "agent.AgentConfigService", - HandlerType: (*AgentConfigServiceServer)(nil), - Methods: []grpc.MethodDesc{ - { - MethodName: "GetAgentConfig", - Handler: _AgentConfigService_GetAgentConfig_Handler, - }, - }, - Streams: []grpc.StreamDesc{ - { - StreamName: "AgentModuleUpdateStream", - Handler: _AgentConfigService_AgentModuleUpdateStream_Handler, - ServerStreams: true, - ClientStreams: true, - }, - }, - Metadata: "agent_config.proto", -} diff --git a/agent/agent/agent/agent_malware.pb.go b/agent/agent/agent/agent_malware.pb.go deleted file mode 100644 index c56a676d2..000000000 --- a/agent/agent/agent/agent_malware.pb.go +++ /dev/null @@ -1,1102 +0,0 @@ -// Code generated by protoc-gen-go. DO NOT EDIT. -// versions: -// protoc-gen-go v1.28.1 -// protoc v3.21.12 -// source: agent_malware.proto - -package agent - -import ( - protoreflect "google.golang.org/protobuf/reflect/protoreflect" - protoimpl "google.golang.org/protobuf/runtime/protoimpl" - reflect "reflect" - sync "sync" -) - -const ( - // Verify that this generated code is sufficiently up-to-date. - _ = protoimpl.EnforceVersion(20 - protoimpl.MinVersion) - // Verify that runtime/protoimpl is sufficiently up-to-date. - _ = protoimpl.EnforceVersion(protoimpl.MaxVersion - 20) -) - -type MalwareStatus int32 - -const ( - MalwareStatus_NEW MalwareStatus = 0 - MalwareStatus_DELETED MalwareStatus = 1 - MalwareStatus_EXCLUDED MalwareStatus = 2 - MalwareStatus_RESTORED MalwareStatus = 3 -) - -// Enum value maps for MalwareStatus. -var ( - MalwareStatus_name = map[int32]string{ - 0: "NEW", - 1: "DELETED", - 2: "EXCLUDED", - 3: "RESTORED", - } - MalwareStatus_value = map[string]int32{ - "NEW": 0, - "DELETED": 1, - "EXCLUDED": 2, - "RESTORED": 3, - } -) - -func (x MalwareStatus) Enum() *MalwareStatus { - p := new(MalwareStatus) - *p = x - return p -} - -func (x MalwareStatus) String() string { - return protoimpl.X.EnumStringOf(x.Descriptor(), protoreflect.EnumNumber(x)) -} - -func (MalwareStatus) Descriptor() protoreflect.EnumDescriptor { - return file_agent_malware_proto_enumTypes[0].Descriptor() -} - -func (MalwareStatus) Type() protoreflect.EnumType { - return &file_agent_malware_proto_enumTypes[0] -} - -func (x MalwareStatus) Number() protoreflect.EnumNumber { - return protoreflect.EnumNumber(x) -} - -// Deprecated: Use MalwareStatus.Descriptor instead. -func (MalwareStatus) EnumDescriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{0} -} - -type ListExclusionResponse struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Exclusions []*AgentMalwareExclusion `protobuf:"bytes,1,rep,name=exclusions,proto3" json:"exclusions,omitempty"` -} - -func (x *ListExclusionResponse) Reset() { - *x = ListExclusionResponse{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[0] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *ListExclusionResponse) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*ListExclusionResponse) ProtoMessage() {} - -func (x *ListExclusionResponse) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[0] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use ListExclusionResponse.ProtoReflect.Descriptor instead. -func (*ListExclusionResponse) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{0} -} - -func (x *ListExclusionResponse) GetExclusions() []*AgentMalwareExclusion { - if x != nil { - return x.Exclusions - } - return nil -} - -type ListExclusionRequest struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - AgentId int64 `protobuf:"varint,1,opt,name=agent_id,json=agentId,proto3" json:"agent_id,omitempty"` -} - -func (x *ListExclusionRequest) Reset() { - *x = ListExclusionRequest{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[1] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *ListExclusionRequest) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*ListExclusionRequest) ProtoMessage() {} - -func (x *ListExclusionRequest) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[1] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use ListExclusionRequest.ProtoReflect.Descriptor instead. -func (*ListExclusionRequest) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{1} -} - -func (x *ListExclusionRequest) GetAgentId() int64 { - if x != nil { - return x.AgentId - } - return 0 -} - -type ChangeStatusRequest struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - MalwareId string `protobuf:"bytes,1,opt,name=malware_id,json=malwareId,proto3" json:"malware_id,omitempty"` - Status MalwareStatus `protobuf:"varint,2,opt,name=status,proto3,enum=agent.MalwareStatus" json:"status,omitempty"` -} - -func (x *ChangeStatusRequest) Reset() { - *x = ChangeStatusRequest{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[2] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *ChangeStatusRequest) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*ChangeStatusRequest) ProtoMessage() {} - -func (x *ChangeStatusRequest) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[2] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use ChangeStatusRequest.ProtoReflect.Descriptor instead. -func (*ChangeStatusRequest) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{2} -} - -func (x *ChangeStatusRequest) GetMalwareId() string { - if x != nil { - return x.MalwareId - } - return "" -} - -func (x *ChangeStatusRequest) GetStatus() MalwareStatus { - if x != nil { - return x.Status - } - return MalwareStatus_NEW -} - -type AgentMalwareDetection struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Id int64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"` - AgentId uint32 `protobuf:"varint,2,opt,name=agent_id,json=agentId,proto3" json:"agent_id,omitempty"` - FilePath string `protobuf:"bytes,3,opt,name=file_path,json=filePath,proto3" json:"file_path,omitempty"` - Sha256 string `protobuf:"bytes,4,opt,name=sha256,proto3" json:"sha256,omitempty"` - Md5 string `protobuf:"bytes,5,opt,name=md5,proto3" json:"md5,omitempty"` - Description string `protobuf:"bytes,6,opt,name=description,proto3" json:"description,omitempty"` - Status MalwareStatus `protobuf:"varint,7,opt,name=status,proto3,enum=agent.MalwareStatus" json:"status,omitempty"` -} - -func (x *AgentMalwareDetection) Reset() { - *x = AgentMalwareDetection{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[3] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *AgentMalwareDetection) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*AgentMalwareDetection) ProtoMessage() {} - -func (x *AgentMalwareDetection) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[3] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use AgentMalwareDetection.ProtoReflect.Descriptor instead. -func (*AgentMalwareDetection) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{3} -} - -func (x *AgentMalwareDetection) GetId() int64 { - if x != nil { - return x.Id - } - return 0 -} - -func (x *AgentMalwareDetection) GetAgentId() uint32 { - if x != nil { - return x.AgentId - } - return 0 -} - -func (x *AgentMalwareDetection) GetFilePath() string { - if x != nil { - return x.FilePath - } - return "" -} - -func (x *AgentMalwareDetection) GetSha256() string { - if x != nil { - return x.Sha256 - } - return "" -} - -func (x *AgentMalwareDetection) GetMd5() string { - if x != nil { - return x.Md5 - } - return "" -} - -func (x *AgentMalwareDetection) GetDescription() string { - if x != nil { - return x.Description - } - return "" -} - -func (x *AgentMalwareDetection) GetStatus() MalwareStatus { - if x != nil { - return x.Status - } - return MalwareStatus_NEW -} - -type AgentMalwareHistory struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Id int64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"` - MalwareId uint32 `protobuf:"varint,2,opt,name=malware_id,json=malwareId,proto3" json:"malware_id,omitempty"` - PrevStatus MalwareStatus `protobuf:"varint,3,opt,name=prev_status,json=prevStatus,proto3,enum=agent.MalwareStatus" json:"prev_status,omitempty"` - ToStatus MalwareStatus `protobuf:"varint,4,opt,name=to_status,json=toStatus,proto3,enum=agent.MalwareStatus" json:"to_status,omitempty"` - ChangedBy string `protobuf:"bytes,5,opt,name=changed_by,json=changedBy,proto3" json:"changed_by,omitempty"` -} - -func (x *AgentMalwareHistory) Reset() { - *x = AgentMalwareHistory{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[4] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *AgentMalwareHistory) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*AgentMalwareHistory) ProtoMessage() {} - -func (x *AgentMalwareHistory) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[4] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use AgentMalwareHistory.ProtoReflect.Descriptor instead. -func (*AgentMalwareHistory) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{4} -} - -func (x *AgentMalwareHistory) GetId() int64 { - if x != nil { - return x.Id - } - return 0 -} - -func (x *AgentMalwareHistory) GetMalwareId() uint32 { - if x != nil { - return x.MalwareId - } - return 0 -} - -func (x *AgentMalwareHistory) GetPrevStatus() MalwareStatus { - if x != nil { - return x.PrevStatus - } - return MalwareStatus_NEW -} - -func (x *AgentMalwareHistory) GetToStatus() MalwareStatus { - if x != nil { - return x.ToStatus - } - return MalwareStatus_NEW -} - -func (x *AgentMalwareHistory) GetChangedBy() string { - if x != nil { - return x.ChangedBy - } - return "" -} - -type AgentMalwareExclusion struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Id int64 `protobuf:"varint,1,opt,name=id,proto3" json:"id,omitempty"` - ExcludeFilePath string `protobuf:"bytes,2,opt,name=exclude_file_path,json=excludeFilePath,proto3" json:"exclude_file_path,omitempty"` - ExcludedBy string `protobuf:"bytes,3,opt,name=excluded_by,json=excludedBy,proto3" json:"excluded_by,omitempty"` - ExcludeDescription string `protobuf:"bytes,4,opt,name=exclude_description,json=excludeDescription,proto3" json:"exclude_description,omitempty"` - AgentId int64 `protobuf:"varint,5,opt,name=agent_id,json=agentId,proto3" json:"agent_id,omitempty"` -} - -func (x *AgentMalwareExclusion) Reset() { - *x = AgentMalwareExclusion{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[5] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *AgentMalwareExclusion) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*AgentMalwareExclusion) ProtoMessage() {} - -func (x *AgentMalwareExclusion) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[5] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use AgentMalwareExclusion.ProtoReflect.Descriptor instead. -func (*AgentMalwareExclusion) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{5} -} - -func (x *AgentMalwareExclusion) GetId() int64 { - if x != nil { - return x.Id - } - return 0 -} - -func (x *AgentMalwareExclusion) GetExcludeFilePath() string { - if x != nil { - return x.ExcludeFilePath - } - return "" -} - -func (x *AgentMalwareExclusion) GetExcludedBy() string { - if x != nil { - return x.ExcludedBy - } - return "" -} - -func (x *AgentMalwareExclusion) GetExcludeDescription() string { - if x != nil { - return x.ExcludeDescription - } - return "" -} - -func (x *AgentMalwareExclusion) GetAgentId() int64 { - if x != nil { - return x.AgentId - } - return 0 -} - -// ListAgentsRequest message definition -type ListMalwareRequest struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - PageNumber int32 `protobuf:"varint,1,opt,name=page_number,json=pageNumber,proto3" json:"page_number,omitempty"` - PageSize int32 `protobuf:"varint,2,opt,name=page_size,json=pageSize,proto3" json:"page_size,omitempty"` - SearchQuery string `protobuf:"bytes,3,opt,name=search_query,json=searchQuery,proto3" json:"search_query,omitempty"` - SortBy []string `protobuf:"bytes,4,rep,name=sort_by,json=sortBy,proto3" json:"sort_by,omitempty"` - SortDescending bool `protobuf:"varint,5,opt,name=sort_descending,json=sortDescending,proto3" json:"sort_descending,omitempty"` -} - -func (x *ListMalwareRequest) Reset() { - *x = ListMalwareRequest{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[6] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *ListMalwareRequest) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*ListMalwareRequest) ProtoMessage() {} - -func (x *ListMalwareRequest) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[6] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use ListMalwareRequest.ProtoReflect.Descriptor instead. -func (*ListMalwareRequest) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{6} -} - -func (x *ListMalwareRequest) GetPageNumber() int32 { - if x != nil { - return x.PageNumber - } - return 0 -} - -func (x *ListMalwareRequest) GetPageSize() int32 { - if x != nil { - return x.PageSize - } - return 0 -} - -func (x *ListMalwareRequest) GetSearchQuery() string { - if x != nil { - return x.SearchQuery - } - return "" -} - -func (x *ListMalwareRequest) GetSortBy() []string { - if x != nil { - return x.SortBy - } - return nil -} - -func (x *ListMalwareRequest) GetSortDescending() bool { - if x != nil { - return x.SortDescending - } - return false -} - -// ListAgentsResponse message definition -type ListMalwareResponse struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Malware []*AgentMalwareDetection `protobuf:"bytes,1,rep,name=malware,proto3" json:"malware,omitempty"` - TotalPages int32 `protobuf:"varint,2,opt,name=total_pages,json=totalPages,proto3" json:"total_pages,omitempty"` - TotalResults int32 `protobuf:"varint,3,opt,name=total_results,json=totalResults,proto3" json:"total_results,omitempty"` -} - -func (x *ListMalwareResponse) Reset() { - *x = ListMalwareResponse{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[7] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *ListMalwareResponse) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*ListMalwareResponse) ProtoMessage() {} - -func (x *ListMalwareResponse) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[7] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use ListMalwareResponse.ProtoReflect.Descriptor instead. -func (*ListMalwareResponse) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{7} -} - -func (x *ListMalwareResponse) GetMalware() []*AgentMalwareDetection { - if x != nil { - return x.Malware - } - return nil -} - -func (x *ListMalwareResponse) GetTotalPages() int32 { - if x != nil { - return x.TotalPages - } - return 0 -} - -func (x *ListMalwareResponse) GetTotalResults() int32 { - if x != nil { - return x.TotalResults - } - return 0 -} - -type ListMalwareHistoryRequest struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - PageNumber int32 `protobuf:"varint,1,opt,name=page_number,json=pageNumber,proto3" json:"page_number,omitempty"` - PageSize int32 `protobuf:"varint,2,opt,name=page_size,json=pageSize,proto3" json:"page_size,omitempty"` - SearchQuery string `protobuf:"bytes,3,opt,name=search_query,json=searchQuery,proto3" json:"search_query,omitempty"` - SortBy []string `protobuf:"bytes,4,rep,name=sort_by,json=sortBy,proto3" json:"sort_by,omitempty"` - SortDescending bool `protobuf:"varint,5,opt,name=sort_descending,json=sortDescending,proto3" json:"sort_descending,omitempty"` -} - -func (x *ListMalwareHistoryRequest) Reset() { - *x = ListMalwareHistoryRequest{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[8] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *ListMalwareHistoryRequest) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*ListMalwareHistoryRequest) ProtoMessage() {} - -func (x *ListMalwareHistoryRequest) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[8] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use ListMalwareHistoryRequest.ProtoReflect.Descriptor instead. -func (*ListMalwareHistoryRequest) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{8} -} - -func (x *ListMalwareHistoryRequest) GetPageNumber() int32 { - if x != nil { - return x.PageNumber - } - return 0 -} - -func (x *ListMalwareHistoryRequest) GetPageSize() int32 { - if x != nil { - return x.PageSize - } - return 0 -} - -func (x *ListMalwareHistoryRequest) GetSearchQuery() string { - if x != nil { - return x.SearchQuery - } - return "" -} - -func (x *ListMalwareHistoryRequest) GetSortBy() []string { - if x != nil { - return x.SortBy - } - return nil -} - -func (x *ListMalwareHistoryRequest) GetSortDescending() bool { - if x != nil { - return x.SortDescending - } - return false -} - -// ListAgentsResponse message definition -type ListMalwareHistoryResponse struct { - state protoimpl.MessageState - sizeCache protoimpl.SizeCache - unknownFields protoimpl.UnknownFields - - Malware []*AgentMalwareHistory `protobuf:"bytes,1,rep,name=malware,proto3" json:"malware,omitempty"` - TotalPages int32 `protobuf:"varint,2,opt,name=total_pages,json=totalPages,proto3" json:"total_pages,omitempty"` - TotalResults int32 `protobuf:"varint,3,opt,name=total_results,json=totalResults,proto3" json:"total_results,omitempty"` -} - -func (x *ListMalwareHistoryResponse) Reset() { - *x = ListMalwareHistoryResponse{} - if protoimpl.UnsafeEnabled { - mi := &file_agent_malware_proto_msgTypes[9] - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - ms.StoreMessageInfo(mi) - } -} - -func (x *ListMalwareHistoryResponse) String() string { - return protoimpl.X.MessageStringOf(x) -} - -func (*ListMalwareHistoryResponse) ProtoMessage() {} - -func (x *ListMalwareHistoryResponse) ProtoReflect() protoreflect.Message { - mi := &file_agent_malware_proto_msgTypes[9] - if protoimpl.UnsafeEnabled && x != nil { - ms := protoimpl.X.MessageStateOf(protoimpl.Pointer(x)) - if ms.LoadMessageInfo() == nil { - ms.StoreMessageInfo(mi) - } - return ms - } - return mi.MessageOf(x) -} - -// Deprecated: Use ListMalwareHistoryResponse.ProtoReflect.Descriptor instead. -func (*ListMalwareHistoryResponse) Descriptor() ([]byte, []int) { - return file_agent_malware_proto_rawDescGZIP(), []int{9} -} - -func (x *ListMalwareHistoryResponse) GetMalware() []*AgentMalwareHistory { - if x != nil { - return x.Malware - } - return nil -} - -func (x *ListMalwareHistoryResponse) GetTotalPages() int32 { - if x != nil { - return x.TotalPages - } - return 0 -} - -func (x *ListMalwareHistoryResponse) GetTotalResults() int32 { - if x != nil { - return x.TotalResults - } - return 0 -} - -var File_agent_malware_proto protoreflect.FileDescriptor - -var file_agent_malware_proto_rawDesc = []byte{ - 0x0a, 0x13, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x5f, 0x6d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x2e, - 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x12, 0x05, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x22, 0x55, 0x0a, 0x15, - 0x4c, 0x69, 0x73, 0x74, 0x45, 0x78, 0x63, 0x6c, 0x75, 0x73, 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x73, - 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x3c, 0x0a, 0x0a, 0x65, 0x78, 0x63, 0x6c, 0x75, 0x73, 0x69, - 0x6f, 0x6e, 0x73, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1c, 0x2e, 0x61, 0x67, 0x65, 0x6e, - 0x74, 0x2e, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x45, 0x78, - 0x63, 0x6c, 0x75, 0x73, 0x69, 0x6f, 0x6e, 0x52, 0x0a, 0x65, 0x78, 0x63, 0x6c, 0x75, 0x73, 0x69, - 0x6f, 0x6e, 0x73, 0x22, 0x31, 0x0a, 0x14, 0x4c, 0x69, 0x73, 0x74, 0x45, 0x78, 0x63, 0x6c, 0x75, - 0x73, 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x19, 0x0a, 0x08, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x07, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x49, 0x64, 0x22, 0x62, 0x0a, 0x13, 0x43, 0x68, 0x61, 0x6e, 0x67, 0x65, - 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x1d, 0x0a, - 0x0a, 0x6d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x5f, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x09, 0x6d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x49, 0x64, 0x12, 0x2c, 0x0a, 0x06, - 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x14, 0x2e, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x53, 0x74, 0x61, 0x74, - 0x75, 0x73, 0x52, 0x06, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x22, 0xd9, 0x01, 0x0a, 0x15, 0x41, - 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x44, 0x65, 0x74, 0x65, 0x63, - 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, - 0x52, 0x02, 0x69, 0x64, 0x12, 0x19, 0x0a, 0x08, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x5f, 0x69, 0x64, - 0x18, 0x02, 0x20, 0x01, 0x28, 0x0d, 0x52, 0x07, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x49, 0x64, 0x12, - 0x1b, 0x0a, 0x09, 0x66, 0x69, 0x6c, 0x65, 0x5f, 0x70, 0x61, 0x74, 0x68, 0x18, 0x03, 0x20, 0x01, - 0x28, 0x09, 0x52, 0x08, 0x66, 0x69, 0x6c, 0x65, 0x50, 0x61, 0x74, 0x68, 0x12, 0x16, 0x0a, 0x06, - 0x73, 0x68, 0x61, 0x32, 0x35, 0x36, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x06, 0x73, 0x68, - 0x61, 0x32, 0x35, 0x36, 0x12, 0x10, 0x0a, 0x03, 0x6d, 0x64, 0x35, 0x18, 0x05, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x03, 0x6d, 0x64, 0x35, 0x12, 0x20, 0x0a, 0x0b, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, - 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x06, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x64, 0x65, 0x73, - 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x2c, 0x0a, 0x06, 0x73, 0x74, 0x61, 0x74, - 0x75, 0x73, 0x18, 0x07, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x14, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, - 0x2e, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x06, - 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x22, 0xcd, 0x01, 0x0a, 0x13, 0x41, 0x67, 0x65, 0x6e, 0x74, - 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x12, 0x0e, - 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x02, 0x69, 0x64, 0x12, 0x1d, - 0x0a, 0x0a, 0x6d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x5f, 0x69, 0x64, 0x18, 0x02, 0x20, 0x01, - 0x28, 0x0d, 0x52, 0x09, 0x6d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x49, 0x64, 0x12, 0x35, 0x0a, - 0x0b, 0x70, 0x72, 0x65, 0x76, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x75, 0x73, 0x18, 0x03, 0x20, 0x01, - 0x28, 0x0e, 0x32, 0x14, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x4d, 0x61, 0x6c, 0x77, 0x61, - 0x72, 0x65, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x0a, 0x70, 0x72, 0x65, 0x76, 0x53, 0x74, - 0x61, 0x74, 0x75, 0x73, 0x12, 0x31, 0x0a, 0x09, 0x74, 0x6f, 0x5f, 0x73, 0x74, 0x61, 0x74, 0x75, - 0x73, 0x18, 0x04, 0x20, 0x01, 0x28, 0x0e, 0x32, 0x14, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, - 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x08, 0x74, - 0x6f, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x1d, 0x0a, 0x0a, 0x63, 0x68, 0x61, 0x6e, 0x67, - 0x65, 0x64, 0x5f, 0x62, 0x79, 0x18, 0x05, 0x20, 0x01, 0x28, 0x09, 0x52, 0x09, 0x63, 0x68, 0x61, - 0x6e, 0x67, 0x65, 0x64, 0x42, 0x79, 0x22, 0xc0, 0x01, 0x0a, 0x15, 0x41, 0x67, 0x65, 0x6e, 0x74, - 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x45, 0x78, 0x63, 0x6c, 0x75, 0x73, 0x69, 0x6f, 0x6e, - 0x12, 0x0e, 0x0a, 0x02, 0x69, 0x64, 0x18, 0x01, 0x20, 0x01, 0x28, 0x03, 0x52, 0x02, 0x69, 0x64, - 0x12, 0x2a, 0x0a, 0x11, 0x65, 0x78, 0x63, 0x6c, 0x75, 0x64, 0x65, 0x5f, 0x66, 0x69, 0x6c, 0x65, - 0x5f, 0x70, 0x61, 0x74, 0x68, 0x18, 0x02, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0f, 0x65, 0x78, 0x63, - 0x6c, 0x75, 0x64, 0x65, 0x46, 0x69, 0x6c, 0x65, 0x50, 0x61, 0x74, 0x68, 0x12, 0x1f, 0x0a, 0x0b, - 0x65, 0x78, 0x63, 0x6c, 0x75, 0x64, 0x65, 0x64, 0x5f, 0x62, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, - 0x09, 0x52, 0x0a, 0x65, 0x78, 0x63, 0x6c, 0x75, 0x64, 0x65, 0x64, 0x42, 0x79, 0x12, 0x2f, 0x0a, - 0x13, 0x65, 0x78, 0x63, 0x6c, 0x75, 0x64, 0x65, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, - 0x74, 0x69, 0x6f, 0x6e, 0x18, 0x04, 0x20, 0x01, 0x28, 0x09, 0x52, 0x12, 0x65, 0x78, 0x63, 0x6c, - 0x75, 0x64, 0x65, 0x44, 0x65, 0x73, 0x63, 0x72, 0x69, 0x70, 0x74, 0x69, 0x6f, 0x6e, 0x12, 0x19, - 0x0a, 0x08, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x5f, 0x69, 0x64, 0x18, 0x05, 0x20, 0x01, 0x28, 0x03, - 0x52, 0x07, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x49, 0x64, 0x22, 0xb7, 0x01, 0x0a, 0x12, 0x4c, 0x69, - 0x73, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, - 0x12, 0x1f, 0x0a, 0x0b, 0x70, 0x61, 0x67, 0x65, 0x5f, 0x6e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x18, - 0x01, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0a, 0x70, 0x61, 0x67, 0x65, 0x4e, 0x75, 0x6d, 0x62, 0x65, - 0x72, 0x12, 0x1b, 0x0a, 0x09, 0x70, 0x61, 0x67, 0x65, 0x5f, 0x73, 0x69, 0x7a, 0x65, 0x18, 0x02, - 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x70, 0x61, 0x67, 0x65, 0x53, 0x69, 0x7a, 0x65, 0x12, 0x21, - 0x0a, 0x0c, 0x73, 0x65, 0x61, 0x72, 0x63, 0x68, 0x5f, 0x71, 0x75, 0x65, 0x72, 0x79, 0x18, 0x03, - 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x73, 0x65, 0x61, 0x72, 0x63, 0x68, 0x51, 0x75, 0x65, 0x72, - 0x79, 0x12, 0x17, 0x0a, 0x07, 0x73, 0x6f, 0x72, 0x74, 0x5f, 0x62, 0x79, 0x18, 0x04, 0x20, 0x03, - 0x28, 0x09, 0x52, 0x06, 0x73, 0x6f, 0x72, 0x74, 0x42, 0x79, 0x12, 0x27, 0x0a, 0x0f, 0x73, 0x6f, - 0x72, 0x74, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x65, 0x6e, 0x64, 0x69, 0x6e, 0x67, 0x18, 0x05, 0x20, - 0x01, 0x28, 0x08, 0x52, 0x0e, 0x73, 0x6f, 0x72, 0x74, 0x44, 0x65, 0x73, 0x63, 0x65, 0x6e, 0x64, - 0x69, 0x6e, 0x67, 0x22, 0x93, 0x01, 0x0a, 0x13, 0x4c, 0x69, 0x73, 0x74, 0x4d, 0x61, 0x6c, 0x77, - 0x61, 0x72, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x36, 0x0a, 0x07, 0x6d, - 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1c, 0x2e, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, - 0x65, 0x44, 0x65, 0x74, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x52, 0x07, 0x6d, 0x61, 0x6c, 0x77, - 0x61, 0x72, 0x65, 0x12, 0x1f, 0x0a, 0x0b, 0x74, 0x6f, 0x74, 0x61, 0x6c, 0x5f, 0x70, 0x61, 0x67, - 0x65, 0x73, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0a, 0x74, 0x6f, 0x74, 0x61, 0x6c, 0x50, - 0x61, 0x67, 0x65, 0x73, 0x12, 0x23, 0x0a, 0x0d, 0x74, 0x6f, 0x74, 0x61, 0x6c, 0x5f, 0x72, 0x65, - 0x73, 0x75, 0x6c, 0x74, 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0c, 0x74, 0x6f, 0x74, - 0x61, 0x6c, 0x52, 0x65, 0x73, 0x75, 0x6c, 0x74, 0x73, 0x22, 0xbe, 0x01, 0x0a, 0x19, 0x4c, 0x69, - 0x73, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, - 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x12, 0x1f, 0x0a, 0x0b, 0x70, 0x61, 0x67, 0x65, 0x5f, - 0x6e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x18, 0x01, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0a, 0x70, 0x61, - 0x67, 0x65, 0x4e, 0x75, 0x6d, 0x62, 0x65, 0x72, 0x12, 0x1b, 0x0a, 0x09, 0x70, 0x61, 0x67, 0x65, - 0x5f, 0x73, 0x69, 0x7a, 0x65, 0x18, 0x02, 0x20, 0x01, 0x28, 0x05, 0x52, 0x08, 0x70, 0x61, 0x67, - 0x65, 0x53, 0x69, 0x7a, 0x65, 0x12, 0x21, 0x0a, 0x0c, 0x73, 0x65, 0x61, 0x72, 0x63, 0x68, 0x5f, - 0x71, 0x75, 0x65, 0x72, 0x79, 0x18, 0x03, 0x20, 0x01, 0x28, 0x09, 0x52, 0x0b, 0x73, 0x65, 0x61, - 0x72, 0x63, 0x68, 0x51, 0x75, 0x65, 0x72, 0x79, 0x12, 0x17, 0x0a, 0x07, 0x73, 0x6f, 0x72, 0x74, - 0x5f, 0x62, 0x79, 0x18, 0x04, 0x20, 0x03, 0x28, 0x09, 0x52, 0x06, 0x73, 0x6f, 0x72, 0x74, 0x42, - 0x79, 0x12, 0x27, 0x0a, 0x0f, 0x73, 0x6f, 0x72, 0x74, 0x5f, 0x64, 0x65, 0x73, 0x63, 0x65, 0x6e, - 0x64, 0x69, 0x6e, 0x67, 0x18, 0x05, 0x20, 0x01, 0x28, 0x08, 0x52, 0x0e, 0x73, 0x6f, 0x72, 0x74, - 0x44, 0x65, 0x73, 0x63, 0x65, 0x6e, 0x64, 0x69, 0x6e, 0x67, 0x22, 0x98, 0x01, 0x0a, 0x1a, 0x4c, - 0x69, 0x73, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, - 0x79, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, 0x12, 0x34, 0x0a, 0x07, 0x6d, 0x61, 0x6c, - 0x77, 0x61, 0x72, 0x65, 0x18, 0x01, 0x20, 0x03, 0x28, 0x0b, 0x32, 0x1a, 0x2e, 0x61, 0x67, 0x65, - 0x6e, 0x74, 0x2e, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x48, - 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x07, 0x6d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x12, - 0x1f, 0x0a, 0x0b, 0x74, 0x6f, 0x74, 0x61, 0x6c, 0x5f, 0x70, 0x61, 0x67, 0x65, 0x73, 0x18, 0x02, - 0x20, 0x01, 0x28, 0x05, 0x52, 0x0a, 0x74, 0x6f, 0x74, 0x61, 0x6c, 0x50, 0x61, 0x67, 0x65, 0x73, - 0x12, 0x23, 0x0a, 0x0d, 0x74, 0x6f, 0x74, 0x61, 0x6c, 0x5f, 0x72, 0x65, 0x73, 0x75, 0x6c, 0x74, - 0x73, 0x18, 0x03, 0x20, 0x01, 0x28, 0x05, 0x52, 0x0c, 0x74, 0x6f, 0x74, 0x61, 0x6c, 0x52, 0x65, - 0x73, 0x75, 0x6c, 0x74, 0x73, 0x2a, 0x41, 0x0a, 0x0d, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, - 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x07, 0x0a, 0x03, 0x4e, 0x45, 0x57, 0x10, 0x00, 0x12, - 0x0b, 0x0a, 0x07, 0x44, 0x45, 0x4c, 0x45, 0x54, 0x45, 0x44, 0x10, 0x01, 0x12, 0x0c, 0x0a, 0x08, - 0x45, 0x58, 0x43, 0x4c, 0x55, 0x44, 0x45, 0x44, 0x10, 0x02, 0x12, 0x0c, 0x0a, 0x08, 0x52, 0x45, - 0x53, 0x54, 0x4f, 0x52, 0x45, 0x44, 0x10, 0x03, 0x32, 0xc9, 0x03, 0x0a, 0x13, 0x41, 0x67, 0x65, - 0x6e, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x53, 0x65, 0x72, 0x76, 0x69, 0x63, 0x65, - 0x12, 0x51, 0x0a, 0x12, 0x47, 0x65, 0x74, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x45, 0x78, 0x63, 0x6c, - 0x75, 0x73, 0x69, 0x6f, 0x6e, 0x73, 0x12, 0x1b, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x4c, - 0x69, 0x73, 0x74, 0x45, 0x78, 0x63, 0x6c, 0x75, 0x73, 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x71, 0x75, - 0x65, 0x73, 0x74, 0x1a, 0x1c, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x4c, 0x69, 0x73, 0x74, - 0x45, 0x78, 0x63, 0x6c, 0x75, 0x73, 0x69, 0x6f, 0x6e, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, - 0x65, 0x22, 0x00, 0x12, 0x59, 0x0a, 0x15, 0x43, 0x72, 0x65, 0x61, 0x74, 0x65, 0x4e, 0x65, 0x77, - 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x45, 0x6e, 0x74, 0x72, 0x79, 0x12, 0x1c, 0x2e, 0x61, - 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, - 0x65, 0x44, 0x65, 0x74, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x1a, 0x1c, 0x2e, 0x61, 0x67, 0x65, - 0x6e, 0x74, 0x2e, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x44, - 0x65, 0x74, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x22, 0x00, 0x28, 0x01, 0x30, 0x01, 0x12, 0x55, - 0x0a, 0x13, 0x43, 0x68, 0x61, 0x6e, 0x67, 0x65, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x53, - 0x74, 0x61, 0x74, 0x75, 0x73, 0x12, 0x1a, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x43, 0x68, - 0x61, 0x6e, 0x67, 0x65, 0x53, 0x74, 0x61, 0x74, 0x75, 0x73, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, - 0x74, 0x1a, 0x1c, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, - 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x44, 0x65, 0x74, 0x65, 0x63, 0x74, 0x69, 0x6f, 0x6e, 0x22, - 0x00, 0x28, 0x01, 0x30, 0x01, 0x12, 0x4b, 0x0a, 0x10, 0x4c, 0x69, 0x73, 0x74, 0x41, 0x67, 0x65, - 0x6e, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x12, 0x19, 0x2e, 0x61, 0x67, 0x65, 0x6e, - 0x74, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x52, 0x65, 0x71, - 0x75, 0x65, 0x73, 0x74, 0x1a, 0x1a, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x4c, 0x69, 0x73, - 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, 0x73, 0x65, - 0x22, 0x00, 0x12, 0x60, 0x0a, 0x17, 0x4c, 0x69, 0x73, 0x74, 0x41, 0x67, 0x65, 0x6e, 0x74, 0x4d, - 0x61, 0x6c, 0x77, 0x61, 0x72, 0x65, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x12, 0x20, 0x2e, - 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x4d, 0x61, 0x6c, 0x77, 0x61, 0x72, - 0x65, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x65, 0x71, 0x75, 0x65, 0x73, 0x74, 0x1a, - 0x21, 0x2e, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2e, 0x4c, 0x69, 0x73, 0x74, 0x4d, 0x61, 0x6c, 0x77, - 0x61, 0x72, 0x65, 0x48, 0x69, 0x73, 0x74, 0x6f, 0x72, 0x79, 0x52, 0x65, 0x73, 0x70, 0x6f, 0x6e, - 0x73, 0x65, 0x22, 0x00, 0x42, 0x32, 0x5a, 0x30, 0x67, 0x69, 0x74, 0x68, 0x75, 0x62, 0x2e, 0x63, - 0x6f, 0x6d, 0x2f, 0x75, 0x74, 0x6d, 0x73, 0x74, 0x61, 0x63, 0x6b, 0x2f, 0x55, 0x54, 0x4d, 0x53, - 0x74, 0x61, 0x63, 0x6b, 0x2f, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x2d, 0x6d, 0x61, 0x6e, 0x61, 0x67, - 0x65, 0x72, 0x2f, 0x61, 0x67, 0x65, 0x6e, 0x74, 0x62, 0x06, 0x70, 0x72, 0x6f, 0x74, 0x6f, 0x33, -} - -var ( - file_agent_malware_proto_rawDescOnce sync.Once - file_agent_malware_proto_rawDescData = file_agent_malware_proto_rawDesc -) - -func file_agent_malware_proto_rawDescGZIP() []byte { - file_agent_malware_proto_rawDescOnce.Do(func() { - file_agent_malware_proto_rawDescData = protoimpl.X.CompressGZIP(file_agent_malware_proto_rawDescData) - }) - return file_agent_malware_proto_rawDescData -} - -var file_agent_malware_proto_enumTypes = make([]protoimpl.EnumInfo, 1) -var file_agent_malware_proto_msgTypes = make([]protoimpl.MessageInfo, 10) -var file_agent_malware_proto_goTypes = []interface{}{ - (MalwareStatus)(0), // 0: agent.MalwareStatus - (*ListExclusionResponse)(nil), // 1: agent.ListExclusionResponse - (*ListExclusionRequest)(nil), // 2: agent.ListExclusionRequest - (*ChangeStatusRequest)(nil), // 3: agent.ChangeStatusRequest - (*AgentMalwareDetection)(nil), // 4: agent.AgentMalwareDetection - (*AgentMalwareHistory)(nil), // 5: agent.AgentMalwareHistory - (*AgentMalwareExclusion)(nil), // 6: agent.AgentMalwareExclusion - (*ListMalwareRequest)(nil), // 7: agent.ListMalwareRequest - (*ListMalwareResponse)(nil), // 8: agent.ListMalwareResponse - (*ListMalwareHistoryRequest)(nil), // 9: agent.ListMalwareHistoryRequest - (*ListMalwareHistoryResponse)(nil), // 10: agent.ListMalwareHistoryResponse -} -var file_agent_malware_proto_depIdxs = []int32{ - 6, // 0: agent.ListExclusionResponse.exclusions:type_name -> agent.AgentMalwareExclusion - 0, // 1: agent.ChangeStatusRequest.status:type_name -> agent.MalwareStatus - 0, // 2: agent.AgentMalwareDetection.status:type_name -> agent.MalwareStatus - 0, // 3: agent.AgentMalwareHistory.prev_status:type_name -> agent.MalwareStatus - 0, // 4: agent.AgentMalwareHistory.to_status:type_name -> agent.MalwareStatus - 4, // 5: agent.ListMalwareResponse.malware:type_name -> agent.AgentMalwareDetection - 5, // 6: agent.ListMalwareHistoryResponse.malware:type_name -> agent.AgentMalwareHistory - 2, // 7: agent.AgentMalwareService.GetAgentExclusions:input_type -> agent.ListExclusionRequest - 4, // 8: agent.AgentMalwareService.CreateNewMalwareEntry:input_type -> agent.AgentMalwareDetection - 3, // 9: agent.AgentMalwareService.ChangeMalwareStatus:input_type -> agent.ChangeStatusRequest - 7, // 10: agent.AgentMalwareService.ListAgentMalware:input_type -> agent.ListMalwareRequest - 9, // 11: agent.AgentMalwareService.ListAgentMalwareHistory:input_type -> agent.ListMalwareHistoryRequest - 1, // 12: agent.AgentMalwareService.GetAgentExclusions:output_type -> agent.ListExclusionResponse - 4, // 13: agent.AgentMalwareService.CreateNewMalwareEntry:output_type -> agent.AgentMalwareDetection - 4, // 14: agent.AgentMalwareService.ChangeMalwareStatus:output_type -> agent.AgentMalwareDetection - 8, // 15: agent.AgentMalwareService.ListAgentMalware:output_type -> agent.ListMalwareResponse - 10, // 16: agent.AgentMalwareService.ListAgentMalwareHistory:output_type -> agent.ListMalwareHistoryResponse - 12, // [12:17] is the sub-list for method output_type - 7, // [7:12] is the sub-list for method input_type - 7, // [7:7] is the sub-list for extension type_name - 7, // [7:7] is the sub-list for extension extendee - 0, // [0:7] is the sub-list for field type_name -} - -func init() { file_agent_malware_proto_init() } -func file_agent_malware_proto_init() { - if File_agent_malware_proto != nil { - return - } - if !protoimpl.UnsafeEnabled { - file_agent_malware_proto_msgTypes[0].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ListExclusionResponse); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_malware_proto_msgTypes[1].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ListExclusionRequest); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_malware_proto_msgTypes[2].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ChangeStatusRequest); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_malware_proto_msgTypes[3].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*AgentMalwareDetection); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_malware_proto_msgTypes[4].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*AgentMalwareHistory); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_malware_proto_msgTypes[5].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*AgentMalwareExclusion); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_malware_proto_msgTypes[6].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ListMalwareRequest); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_malware_proto_msgTypes[7].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ListMalwareResponse); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_malware_proto_msgTypes[8].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ListMalwareHistoryRequest); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - file_agent_malware_proto_msgTypes[9].Exporter = func(v interface{}, i int) interface{} { - switch v := v.(*ListMalwareHistoryResponse); i { - case 0: - return &v.state - case 1: - return &v.sizeCache - case 2: - return &v.unknownFields - default: - return nil - } - } - } - type x struct{} - out := protoimpl.TypeBuilder{ - File: protoimpl.DescBuilder{ - GoPackagePath: reflect.TypeOf(x{}).PkgPath(), - RawDescriptor: file_agent_malware_proto_rawDesc, - NumEnums: 1, - NumMessages: 10, - NumExtensions: 0, - NumServices: 1, - }, - GoTypes: file_agent_malware_proto_goTypes, - DependencyIndexes: file_agent_malware_proto_depIdxs, - EnumInfos: file_agent_malware_proto_enumTypes, - MessageInfos: file_agent_malware_proto_msgTypes, - }.Build() - File_agent_malware_proto = out.File - file_agent_malware_proto_rawDesc = nil - file_agent_malware_proto_goTypes = nil - file_agent_malware_proto_depIdxs = nil -} diff --git a/agent/agent/agent/agent_malware_grpc.pb.go b/agent/agent/agent/agent_malware_grpc.pb.go deleted file mode 100644 index 0349889c9..000000000 --- a/agent/agent/agent/agent_malware_grpc.pb.go +++ /dev/null @@ -1,262 +0,0 @@ -// Code generated by protoc-gen-go-grpc. DO NOT EDIT. -// versions: -// - protoc-gen-go-grpc v1.5.1 -// - protoc v3.21.12 -// source: agent_malware.proto - -package agent - -import ( - context "context" - grpc "google.golang.org/grpc" - codes "google.golang.org/grpc/codes" - status "google.golang.org/grpc/status" -) - -// This is a compile-time assertion to ensure that this generated file -// is compatible with the grpc package it is being compiled against. -// Requires gRPC-Go v1.64.0 or later. -const _ = grpc.SupportPackageIsVersion9 - -const ( - AgentMalwareService_GetAgentExclusions_FullMethodName = "/agent.AgentMalwareService/GetAgentExclusions" - AgentMalwareService_CreateNewMalwareEntry_FullMethodName = "/agent.AgentMalwareService/CreateNewMalwareEntry" - AgentMalwareService_ChangeMalwareStatus_FullMethodName = "/agent.AgentMalwareService/ChangeMalwareStatus" - AgentMalwareService_ListAgentMalware_FullMethodName = "/agent.AgentMalwareService/ListAgentMalware" - AgentMalwareService_ListAgentMalwareHistory_FullMethodName = "/agent.AgentMalwareService/ListAgentMalwareHistory" -) - -// AgentMalwareServiceClient is the client API for AgentMalwareService service. -// -// For semantics around ctx use and closing/ending streaming RPCs, please refer to https://pkg.go.dev/google.golang.org/grpc/?tab=doc#ClientConn.NewStream. -type AgentMalwareServiceClient interface { - GetAgentExclusions(ctx context.Context, in *ListExclusionRequest, opts ...grpc.CallOption) (*ListExclusionResponse, error) - CreateNewMalwareEntry(ctx context.Context, opts ...grpc.CallOption) (grpc.BidiStreamingClient[AgentMalwareDetection, AgentMalwareDetection], error) - ChangeMalwareStatus(ctx context.Context, opts ...grpc.CallOption) (grpc.BidiStreamingClient[ChangeStatusRequest, AgentMalwareDetection], error) - ListAgentMalware(ctx context.Context, in *ListMalwareRequest, opts ...grpc.CallOption) (*ListMalwareResponse, error) - ListAgentMalwareHistory(ctx context.Context, in *ListMalwareHistoryRequest, opts ...grpc.CallOption) (*ListMalwareHistoryResponse, error) -} - -type agentMalwareServiceClient struct { - cc grpc.ClientConnInterface -} - -func NewAgentMalwareServiceClient(cc grpc.ClientConnInterface) AgentMalwareServiceClient { - return &agentMalwareServiceClient{cc} -} - -func (c *agentMalwareServiceClient) GetAgentExclusions(ctx context.Context, in *ListExclusionRequest, opts ...grpc.CallOption) (*ListExclusionResponse, error) { - cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) - out := new(ListExclusionResponse) - err := c.cc.Invoke(ctx, AgentMalwareService_GetAgentExclusions_FullMethodName, in, out, cOpts...) - if err != nil { - return nil, err - } - return out, nil -} - -func (c *agentMalwareServiceClient) CreateNewMalwareEntry(ctx context.Context, opts ...grpc.CallOption) (grpc.BidiStreamingClient[AgentMalwareDetection, AgentMalwareDetection], error) { - cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) - stream, err := c.cc.NewStream(ctx, &AgentMalwareService_ServiceDesc.Streams[0], AgentMalwareService_CreateNewMalwareEntry_FullMethodName, cOpts...) - if err != nil { - return nil, err - } - x := &grpc.GenericClientStream[AgentMalwareDetection, AgentMalwareDetection]{ClientStream: stream} - return x, nil -} - -// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name. -type AgentMalwareService_CreateNewMalwareEntryClient = grpc.BidiStreamingClient[AgentMalwareDetection, AgentMalwareDetection] - -func (c *agentMalwareServiceClient) ChangeMalwareStatus(ctx context.Context, opts ...grpc.CallOption) (grpc.BidiStreamingClient[ChangeStatusRequest, AgentMalwareDetection], error) { - cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) - stream, err := c.cc.NewStream(ctx, &AgentMalwareService_ServiceDesc.Streams[1], AgentMalwareService_ChangeMalwareStatus_FullMethodName, cOpts...) - if err != nil { - return nil, err - } - x := &grpc.GenericClientStream[ChangeStatusRequest, AgentMalwareDetection]{ClientStream: stream} - return x, nil -} - -// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name. -type AgentMalwareService_ChangeMalwareStatusClient = grpc.BidiStreamingClient[ChangeStatusRequest, AgentMalwareDetection] - -func (c *agentMalwareServiceClient) ListAgentMalware(ctx context.Context, in *ListMalwareRequest, opts ...grpc.CallOption) (*ListMalwareResponse, error) { - cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) - out := new(ListMalwareResponse) - err := c.cc.Invoke(ctx, AgentMalwareService_ListAgentMalware_FullMethodName, in, out, cOpts...) - if err != nil { - return nil, err - } - return out, nil -} - -func (c *agentMalwareServiceClient) ListAgentMalwareHistory(ctx context.Context, in *ListMalwareHistoryRequest, opts ...grpc.CallOption) (*ListMalwareHistoryResponse, error) { - cOpts := append([]grpc.CallOption{grpc.StaticMethod()}, opts...) - out := new(ListMalwareHistoryResponse) - err := c.cc.Invoke(ctx, AgentMalwareService_ListAgentMalwareHistory_FullMethodName, in, out, cOpts...) - if err != nil { - return nil, err - } - return out, nil -} - -// AgentMalwareServiceServer is the server API for AgentMalwareService service. -// All implementations must embed UnimplementedAgentMalwareServiceServer -// for forward compatibility. -type AgentMalwareServiceServer interface { - GetAgentExclusions(context.Context, *ListExclusionRequest) (*ListExclusionResponse, error) - CreateNewMalwareEntry(grpc.BidiStreamingServer[AgentMalwareDetection, AgentMalwareDetection]) error - ChangeMalwareStatus(grpc.BidiStreamingServer[ChangeStatusRequest, AgentMalwareDetection]) error - ListAgentMalware(context.Context, *ListMalwareRequest) (*ListMalwareResponse, error) - ListAgentMalwareHistory(context.Context, *ListMalwareHistoryRequest) (*ListMalwareHistoryResponse, error) - mustEmbedUnimplementedAgentMalwareServiceServer() -} - -// UnimplementedAgentMalwareServiceServer must be embedded to have -// forward compatible implementations. -// -// NOTE: this should be embedded by value instead of pointer to avoid a nil -// pointer dereference when methods are called. -type UnimplementedAgentMalwareServiceServer struct{} - -func (UnimplementedAgentMalwareServiceServer) GetAgentExclusions(context.Context, *ListExclusionRequest) (*ListExclusionResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method GetAgentExclusions not implemented") -} -func (UnimplementedAgentMalwareServiceServer) CreateNewMalwareEntry(grpc.BidiStreamingServer[AgentMalwareDetection, AgentMalwareDetection]) error { - return status.Errorf(codes.Unimplemented, "method CreateNewMalwareEntry not implemented") -} -func (UnimplementedAgentMalwareServiceServer) ChangeMalwareStatus(grpc.BidiStreamingServer[ChangeStatusRequest, AgentMalwareDetection]) error { - return status.Errorf(codes.Unimplemented, "method ChangeMalwareStatus not implemented") -} -func (UnimplementedAgentMalwareServiceServer) ListAgentMalware(context.Context, *ListMalwareRequest) (*ListMalwareResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method ListAgentMalware not implemented") -} -func (UnimplementedAgentMalwareServiceServer) ListAgentMalwareHistory(context.Context, *ListMalwareHistoryRequest) (*ListMalwareHistoryResponse, error) { - return nil, status.Errorf(codes.Unimplemented, "method ListAgentMalwareHistory not implemented") -} -func (UnimplementedAgentMalwareServiceServer) mustEmbedUnimplementedAgentMalwareServiceServer() {} -func (UnimplementedAgentMalwareServiceServer) testEmbeddedByValue() {} - -// UnsafeAgentMalwareServiceServer may be embedded to opt out of forward compatibility for this service. -// Use of this interface is not recommended, as added methods to AgentMalwareServiceServer will -// result in compilation errors. -type UnsafeAgentMalwareServiceServer interface { - mustEmbedUnimplementedAgentMalwareServiceServer() -} - -func RegisterAgentMalwareServiceServer(s grpc.ServiceRegistrar, srv AgentMalwareServiceServer) { - // If the following call pancis, it indicates UnimplementedAgentMalwareServiceServer was - // embedded by pointer and is nil. This will cause panics if an - // unimplemented method is ever invoked, so we test this at initialization - // time to prevent it from happening at runtime later due to I/O. - if t, ok := srv.(interface{ testEmbeddedByValue() }); ok { - t.testEmbeddedByValue() - } - s.RegisterService(&AgentMalwareService_ServiceDesc, srv) -} - -func _AgentMalwareService_GetAgentExclusions_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(ListExclusionRequest) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(AgentMalwareServiceServer).GetAgentExclusions(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: AgentMalwareService_GetAgentExclusions_FullMethodName, - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(AgentMalwareServiceServer).GetAgentExclusions(ctx, req.(*ListExclusionRequest)) - } - return interceptor(ctx, in, info, handler) -} - -func _AgentMalwareService_CreateNewMalwareEntry_Handler(srv interface{}, stream grpc.ServerStream) error { - return srv.(AgentMalwareServiceServer).CreateNewMalwareEntry(&grpc.GenericServerStream[AgentMalwareDetection, AgentMalwareDetection]{ServerStream: stream}) -} - -// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name. -type AgentMalwareService_CreateNewMalwareEntryServer = grpc.BidiStreamingServer[AgentMalwareDetection, AgentMalwareDetection] - -func _AgentMalwareService_ChangeMalwareStatus_Handler(srv interface{}, stream grpc.ServerStream) error { - return srv.(AgentMalwareServiceServer).ChangeMalwareStatus(&grpc.GenericServerStream[ChangeStatusRequest, AgentMalwareDetection]{ServerStream: stream}) -} - -// This type alias is provided for backwards compatibility with existing code that references the prior non-generic stream type by name. -type AgentMalwareService_ChangeMalwareStatusServer = grpc.BidiStreamingServer[ChangeStatusRequest, AgentMalwareDetection] - -func _AgentMalwareService_ListAgentMalware_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(ListMalwareRequest) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(AgentMalwareServiceServer).ListAgentMalware(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: AgentMalwareService_ListAgentMalware_FullMethodName, - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(AgentMalwareServiceServer).ListAgentMalware(ctx, req.(*ListMalwareRequest)) - } - return interceptor(ctx, in, info, handler) -} - -func _AgentMalwareService_ListAgentMalwareHistory_Handler(srv interface{}, ctx context.Context, dec func(interface{}) error, interceptor grpc.UnaryServerInterceptor) (interface{}, error) { - in := new(ListMalwareHistoryRequest) - if err := dec(in); err != nil { - return nil, err - } - if interceptor == nil { - return srv.(AgentMalwareServiceServer).ListAgentMalwareHistory(ctx, in) - } - info := &grpc.UnaryServerInfo{ - Server: srv, - FullMethod: AgentMalwareService_ListAgentMalwareHistory_FullMethodName, - } - handler := func(ctx context.Context, req interface{}) (interface{}, error) { - return srv.(AgentMalwareServiceServer).ListAgentMalwareHistory(ctx, req.(*ListMalwareHistoryRequest)) - } - return interceptor(ctx, in, info, handler) -} - -// AgentMalwareService_ServiceDesc is the grpc.ServiceDesc for AgentMalwareService service. -// It's only intended for direct use with grpc.RegisterService, -// and not to be introspected or modified (even as a copy) -var AgentMalwareService_ServiceDesc = grpc.ServiceDesc{ - ServiceName: "agent.AgentMalwareService", - HandlerType: (*AgentMalwareServiceServer)(nil), - Methods: []grpc.MethodDesc{ - { - MethodName: "GetAgentExclusions", - Handler: _AgentMalwareService_GetAgentExclusions_Handler, - }, - { - MethodName: "ListAgentMalware", - Handler: _AgentMalwareService_ListAgentMalware_Handler, - }, - { - MethodName: "ListAgentMalwareHistory", - Handler: _AgentMalwareService_ListAgentMalwareHistory_Handler, - }, - }, - Streams: []grpc.StreamDesc{ - { - StreamName: "CreateNewMalwareEntry", - Handler: _AgentMalwareService_CreateNewMalwareEntry_Handler, - ServerStreams: true, - ClientStreams: true, - }, - { - StreamName: "ChangeMalwareStatus", - Handler: _AgentMalwareService_ChangeMalwareStatus_Handler, - ServerStreams: true, - ClientStreams: true, - }, - }, - Metadata: "agent_malware.proto", -} diff --git a/agent/agent/agent/delete.go b/agent/agent/agent/delete.go deleted file mode 100644 index f812f66d4..000000000 --- a/agent/agent/agent/delete.go +++ /dev/null @@ -1,63 +0,0 @@ -package agent - -import ( - context "context" - "fmt" - "os/user" - "strconv" - "time" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/utils" - grpc "google.golang.org/grpc" - "google.golang.org/grpc/metadata" -) - -const ( - maxConnectionAttempts = 3 - initialReconnectDelay = 10 * time.Second - maxReconnectDelay = 60 * time.Second -) - -func DeleteAgent(conn *grpc.ClientConn, cnf *configuration.Config, h *logger.Logger) error { - connectionAttemps := 0 - reconnectDelay := initialReconnectDelay - - // Create a client for AgentService - agentClient := NewAgentServiceClient(conn) - ctx, cancel := context.WithCancel(context.Background()) - defer cancel() - ctx = metadata.AppendToOutgoingContext(ctx, "key", cnf.AgentKey) - ctx = metadata.AppendToOutgoingContext(ctx, "id", strconv.Itoa(int(cnf.AgentID))) - - currentUser, err := user.Current() - if err != nil { - return fmt.Errorf("error getting user: %v", err) - } - - delet := &AgentDelete{ - DeletedBy: currentUser.Username, - } - - for { - if connectionAttemps >= maxConnectionAttempts { - return fmt.Errorf("error removing UTMStack Agent from Agent Manager") - } - h.Info("trying to remove UTMStack Agent from Agent Manager...") - - _, err = agentClient.DeleteAgent(ctx, delet) - if err != nil { - connectionAttemps++ - h.Info("error removing UTMStack Agent from Agent Manager, trying again in %.0f seconds", reconnectDelay.Seconds()) - time.Sleep(reconnectDelay) - reconnectDelay = utils.IncrementReconnectDelay(reconnectDelay, maxReconnectDelay) - continue - } - - break - } - - h.Info("UTMStack Agent removed successfully") - return nil -} diff --git a/agent/agent/agent/incident_response.go b/agent/agent/agent/incident_response.go deleted file mode 100644 index 9fec23793..000000000 --- a/agent/agent/agent/incident_response.go +++ /dev/null @@ -1,107 +0,0 @@ -package agent - -import ( - "context" - "io" - "runtime" - "time" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/utils" - "google.golang.org/protobuf/types/known/timestamppb" -) - -func IncidentResponseStream(client AgentServiceClient, ctx context.Context, cnf *configuration.Config, h *logger.Logger) { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - h.Fatal("Failed to get current path: %v", err) - } - - connectionTime := 0 * time.Second - reconnectDelay := configuration.InitialReconnectDelay - var connErrMsgWritten bool - - for { - if connectionTime >= configuration.MaxConnectionTime { - connectionTime = 0 * time.Second - reconnectDelay = configuration.InitialReconnectDelay - continue - } - - stream, err := client.AgentStream(ctx) - if err != nil { - if !connErrMsgWritten { - h.ErrorF("failed to start AgentStream: %v", err) - connErrMsgWritten = true - } - - time.Sleep(reconnectDelay) - connectionTime = utils.IncrementReconnectTime(connectionTime, reconnectDelay, configuration.MaxConnectionTime) - reconnectDelay = utils.IncrementReconnectDelay(reconnectDelay, configuration.MaxReconnectDelay) - continue - } - - connErrMsgWritten = false - - // Handle the bidirectional stream - for { - in, err := stream.Recv() - if err == io.EOF { - // Server closed the stream - break - } - if err != nil { - h.ErrorF("error receiving command from server: %v", err) - break - } - - switch msg := in.StreamMessage.(type) { - case *BidirectionalStream_Command: - // Handle the received command - err = commandProcessor(h, path, stream, cnf, []string{msg.Command.Command, in.GetCommand().CmdId}) - if err == io.EOF { - break - } - if err != nil { - h.ErrorF("failed to send result to server: %v", err) - } - } - } - } -} - -func commandProcessor(h *logger.Logger, path string, stream AgentService_AgentStreamClient, cnf *configuration.Config, commandPair []string) error { - var result string - var errB bool - - h.Info("Received command: %s", commandPair[0]) - - switch runtime.GOOS { - case "windows": - result, errB = utils.ExecuteWithResult("cmd.exe", path, "/C", commandPair[0]) - case "linux": - result, errB = utils.ExecuteWithResult("sh", path, "-c", commandPair[0]) - default: - h.Fatal("unsupported operating system: %s", runtime.GOOS) - } - - if errB { - h.ErrorF("error executing command %s: %s", commandPair[0], result) - } else { - h.Info("Result when executing the command %s: %s", commandPair[0], result) - } - - // Send the result back to the server - if err := stream.Send(&BidirectionalStream{ - StreamMessage: &BidirectionalStream_Result{ - Result: &CommandResult{Result: result, AgentKey: cnf.AgentKey, ExecutedAt: timestamppb.Now(), CmdId: commandPair[1]}, - }, - }); err != nil { - return err - } else { - h.Info("Result sent to server successfully!!!") - } - return nil -} diff --git a/agent/agent/agent/ping_imp.go b/agent/agent/agent/ping_imp.go deleted file mode 100644 index 2bca835cc..000000000 --- a/agent/agent/agent/ping_imp.go +++ /dev/null @@ -1,56 +0,0 @@ -package agent - -import ( - "context" - "io" - "time" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/utils" -) - -// Call this function to start sending Ping requests -func StartPing(client PingServiceClient, ctx context.Context, cnf *configuration.Config, h *logger.Logger) { - connectionTime := 0 * time.Second - reconnectDelay := configuration.InitialReconnectDelay - var connErrMsgWritten bool - - for { - if connectionTime >= configuration.MaxConnectionTime { - connectionTime = 0 * time.Second - reconnectDelay = configuration.InitialReconnectDelay - continue - } - - stream, err := client.Ping(ctx) - if err != nil { - if !connErrMsgWritten { - h.ErrorF("failed to start Ping Stream: %v", err) - connErrMsgWritten = true - } - time.Sleep(reconnectDelay) - connectionTime = utils.IncrementReconnectTime(connectionTime, reconnectDelay, configuration.MaxConnectionTime) - reconnectDelay = utils.IncrementReconnectDelay(reconnectDelay, configuration.MaxReconnectDelay) - continue - } - - connErrMsgWritten = false - - ticker := time.NewTicker(15 * time.Second) - defer ticker.Stop() - - for range ticker.C { - err := stream.Send(&PingRequest{Type: ConnectorType_AGENT}) - if err == io.EOF { - // Server closed the stream - h.ErrorF("Server closed the stream: %v", err) - break - } - if err != nil { - h.ErrorF("Error sending Ping request: %v", err) - break - } - } - } -} diff --git a/agent/agent/agent/uninstall.go b/agent/agent/agent/uninstall.go deleted file mode 100644 index 2716b064f..000000000 --- a/agent/agent/agent/uninstall.go +++ /dev/null @@ -1,30 +0,0 @@ -package agent - -import ( - "fmt" - "path/filepath" - "runtime" - - "github.com/utmstack/UTMStack/agent/agent/utils" -) - -func UninstallAll() error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } - - var exeName string - switch runtime.GOOS { - case "windows": - exeName = filepath.Join(path, "utmstack-runner-windows.exe") - case "linux": - exeName = filepath.Join(path, "utmstack-runner-linux") - } - - err = utils.Execute(exeName, path, "uninstall") - if err != nil { - return fmt.Errorf("%v", err) - } - return nil -} diff --git a/agent/agent/agent/update.go b/agent/agent/agent/update.go deleted file mode 100644 index 62239f057..000000000 --- a/agent/agent/agent/update.go +++ /dev/null @@ -1,37 +0,0 @@ -package agent - -import ( - context "context" - "fmt" - - "github.com/utmstack/UTMStack/agent/agent/utils" -) - -func UpdateAgent(client AgentServiceClient, ctx context.Context) error { - osInfo, err := utils.GetOsInfo() - if err != nil { - return fmt.Errorf("error getting os info: %v", err) - } - - version, err := GetVersion() - if err != nil { - return fmt.Errorf("error getting agent version: %v", err) - } - - request := &AgentRequest{ - Hostname: osInfo.Hostname, - Version: version, - Mac: osInfo.Mac, - OsMajorVersion: osInfo.OsMajorVersion, - OsMinorVersion: osInfo.OsMinorVersion, - Aliases: osInfo.Aliases, - Addresses: osInfo.Addresses, - } - - _, err = client.UpdateAgent(ctx, request) - if err != nil { - return fmt.Errorf("error updating agent: %v", err) - } - - return nil -} diff --git a/agent/agent/agent/version.go b/agent/agent/agent/version.go deleted file mode 100644 index 1ee56332c..000000000 --- a/agent/agent/agent/version.go +++ /dev/null @@ -1,30 +0,0 @@ -package agent - -import ( - "fmt" - "path/filepath" - - "github.com/utmstack/UTMStack/agent/agent/utils" -) - -type Version struct { - MasterVersion string `json:"master_version"` - AgentVersion string `json:"agent_version"` - UpdaterVersion string `json:"updater_version"` - RedlineVersion string `json:"redline_version"` -} - -func GetVersion() (string, error) { - path, err := utils.GetMyPath() - if err != nil { - return "", fmt.Errorf("failed to get current path: %v", err) - } - - versions := &Version{} - err = utils.ReadJson(filepath.Join(path, "versions.json"), &versions) - if err != nil { - return "", fmt.Errorf("error reading current versions.json: %v", err) - } - - return versions.AgentVersion, nil -} diff --git a/agent/agent/agent/agent_grpc.pb.go b/agent/agent/agent_grpc.pb.go similarity index 100% rename from agent/agent/agent/agent_grpc.pb.go rename to agent/agent/agent_grpc.pb.go diff --git a/agent/agent/beats/beat.go b/agent/agent/beats/beat.go deleted file mode 100644 index 52e84d71a..000000000 --- a/agent/agent/beats/beat.go +++ /dev/null @@ -1,69 +0,0 @@ -package beats - -import ( - "fmt" - "runtime" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" -) - -type BeatConfig struct { - LogsPath string - LogFileName string -} - -type Beat interface { - Install() error - SendSystemLogs(h *logger.Logger) - Uninstall() error -} - -func getBeatsInstances() []Beat { - var beatsInstance []Beat - switch runtime.GOOS { - case "windows": - beatsInstance = append(beatsInstance, Winlogbeat{}) - beatsInstance = append(beatsInstance, Filebeat{}) - case "linux": - beatsInstance = append(beatsInstance, Filebeat{}) - } - - return beatsInstance -} - -func InstallBeats(cnf configuration.Config, h *logger.Logger) error { - beatsInstances := getBeatsInstances() - - for _, beat := range beatsInstances { - err := beat.Install() - if err != nil { - return fmt.Errorf("%v", err) - } - } - - h.Info("beats installed correctly") - - return nil -} - -func BeatsLogsReader(h *logger.Logger) { - beatsInstances := getBeatsInstances() - for _, beat := range beatsInstances { - go beat.SendSystemLogs(h) - } -} - -func UninstallBeats(h *logger.Logger) error { - beatsInstances := getBeatsInstances() - - for _, beat := range beatsInstances { - err := beat.Uninstall() - if err != nil { - return fmt.Errorf("%v", err) - } - } - - h.Info("beats uninstalled correctly") - return nil -} diff --git a/agent/agent/agent/common.pb.go b/agent/agent/common.pb.go similarity index 100% rename from agent/agent/agent/common.pb.go rename to agent/agent/common.pb.go diff --git a/agent/agent/configuration/const.go b/agent/agent/configuration/const.go deleted file mode 100644 index 5f3f1f08d..000000000 --- a/agent/agent/configuration/const.go +++ /dev/null @@ -1,157 +0,0 @@ -package configuration - -import ( - "path/filepath" - "runtime" - "time" - - "github.com/utmstack/UTMStack/agent/agent/utils" -) - -const REPLACE_KEY string = "" - -const ( - AGENTMANAGERPORT string = "9000" - AUTHLOGSPORT string = "50051" - BatchCapacity = 100 - MaxConnectionTime = 120 * time.Second - InitialReconnectDelay = 10 * time.Second - MaxReconnectDelay = 120 * time.Second - - SERV_NAME = "UTMStackAgent" - SERV_LOG = "utmstack_agent.log" - ModulesServName = "UTMStackModulesLogsCollector" - WinServName = "UTMStackWindowsLogsCollector" - ModulesLockName = "utmstack_modules_collector.lock" - WinLockName = "utmstack_windows_collector.lock" - RedlineLockName = "utmstack_redline.lock" - RedlineServName = "UTMStackRedline" - CollectorFileName = "log-collector-configuration.json" - CollectorFileNameOld = "log-collector-config.json" - UUIDFileName = "uuid.yml" - MESSAGE_HEADER = "utm_stack_agent_ds" - BatchToSend = 5 - PortRangeMin = "7000" - PortRangeMax = "9000" -) - -type LogType string - -const ( - LogTypeWindowsAgent LogType = "beats_windows_agent" - LogTypeSyslog LogType = "syslog" - LogTypeVmware LogType = "vmware" - LogTypeLinuxAgent LogType = "beats_linux_agent" - LogTypeEset LogType = "antivirus_eset" - LogTypeKaspersky LogType = "antivirus_kaspersky" - LogTypeTraefikModule LogType = "beats_traefik_module" - LogTypeMongodbModule LogType = "beats_mongodb_module" - LogTypeMysqlModule LogType = "beats_mysql_module" - LogTypePostgresqlModule LogType = "beats_postgresql_module" - LogTypeRedisModule LogType = "beats_redis_module" - LogTypeElasticsearchModule LogType = "beats_elasticsearch_module" - LogTypeKafkaModule LogType = "beats_kafka_module" - LogTypeKibanaModule LogType = "beats_kibana_module" - LogTypeLogstashModule LogType = "beats_logstash_module" - LogTypeCiscoAsa LogType = "cisco_asa" - LogTypeCiscoMeraki LogType = "cisco_meraki" - LogTypeFortinet LogType = "firewall_fortinet" - LogTypePaloalto LogType = "firewall_paloalto" - LogTypeMikrotik LogType = "firewall_mikrotik" - LogTypeCiscoFirepower LogType = "cisco_firepower" - LogTypeSophosXG LogType = "firewall_sophos" - LogTypeCiscoSwitch LogType = "cisco_switch" - LogTypeSonicwall LogType = "firewall_sonicwall" - LogTypeNatsModule LogType = "beats_nats_module" - LogTypeDeceptivebytes LogType = "antivirus_deceptivebytes" - LogTypeOsqueryModule LogType = "beats_osquery_module" - LogTypeLinuxAuditdModule LogType = "beats_auditd_module" - LogTypeHaproxyModule LogType = "beats_haproxy_module" - LogTypeNginxModule LogType = "beats_nginx_module" - LogTypeIisModule LogType = "beats_iis_module" - LogTypeApacheModule LogType = "beats_apache_module" - LogTypeSentinelOne LogType = "antivirus_sentinel_one" - LogTypeCiscoGeneric LogType = "cisco" - LogTypeMacOs LogType = "macos_logs" - LogTypeGeneric LogType = "generic" - LogTypeNetflow LogType = "netflow" - LogTypeAix LogType = "ibm_aix" - LogTypePfsense LogType = "firewall_pfsense" - LogTypeFortiweb LogType = "firewall_fortiweb" -) - -type ProtoPort struct { - UDP string - TCP string -} - -var ( - ProtoPorts = map[LogType]ProtoPort{ - LogTypeSyslog: {UDP: "7014", TCP: "7014"}, - LogTypeVmware: {UDP: "7002", TCP: "7002"}, - LogTypeEset: {UDP: "7003", TCP: "7003"}, - LogTypeKaspersky: {UDP: "7004", TCP: "7004"}, - LogTypeCiscoGeneric: {UDP: "514", TCP: "1470"}, - LogTypeFortinet: {UDP: "7005", TCP: "7005"}, - LogTypePaloalto: {UDP: "7006", TCP: "7006"}, - LogTypeMikrotik: {UDP: "7007", TCP: "7007"}, - LogTypeSophosXG: {UDP: "7008", TCP: "7008"}, - LogTypeSonicwall: {UDP: "7009", TCP: "7009"}, - LogTypeDeceptivebytes: {UDP: "7010", TCP: "7010"}, - LogTypeSentinelOne: {UDP: "7012", TCP: "7012"}, - LogTypeMacOs: {UDP: "7015", TCP: "7015"}, - LogTypeAix: {UDP: "7016", TCP: "7016"}, - LogTypePfsense: {UDP: "7017", TCP: "7017"}, - LogTypeFortiweb: {UDP: "7018", TCP: "7018"}, - LogTypeNetflow: {UDP: "2055", TCP: ""}, - } - - ProhibitedPortsChange = []LogType{LogTypeCiscoGeneric, LogTypeNetflow} -) - -func GetCaPath() string { - path, _ := utils.GetMyPath() - return filepath.Join(path, "certs", "ca.crt") -} - -func GetCollectorConfigPath() string { - path, _ := utils.GetMyPath() - return filepath.Join(path, CollectorFileName) -} - -func GetCollectorConfigPathOld() string { - path, _ := utils.GetMyPath() - return filepath.Join(path, CollectorFileNameOld) -} - -func GetAgentBin() string { - var bin string - switch runtime.GOOS { - case "windows": - bin = "utmstack_agent_service.exe" - case "linux": - bin = "utmstack_agent_service" - } - return bin -} - -func GetMessageFormated(host string, msg string) string { - return "[" + MESSAGE_HEADER + "=" + host + "]-" + msg -} - -func ValidateModuleType(typ LogType) string { - switch typ { - case LogTypeSyslog, LogTypeVmware, LogTypeEset, LogTypeKaspersky, LogTypeFortinet, LogTypePaloalto, - LogTypeMikrotik, LogTypeSophosXG, LogTypeSonicwall, LogTypeSentinelOne, LogTypeCiscoGeneric, LogTypeMacOs, - LogTypeDeceptivebytes, LogTypeAix, LogTypePfsense, LogTypeFortiweb: - return "syslog" - case LogTypeNetflow: - return "netflow" - case LogTypeWindowsAgent, LogTypeLinuxAgent, LogTypeTraefikModule, LogTypeMongodbModule, LogTypeMysqlModule, LogTypePostgresqlModule, - LogTypeRedisModule, LogTypeElasticsearchModule, LogTypeKafkaModule, LogTypeKibanaModule, LogTypeLogstashModule, LogTypeNatsModule, - LogTypeOsqueryModule, LogTypeLinuxAuditdModule, LogTypeHaproxyModule, LogTypeNginxModule, LogTypeIisModule, LogTypeApacheModule: - return "beats" - default: - return "nil" - } -} diff --git a/agent/agent/conn/conn.go b/agent/agent/conn/conn.go deleted file mode 100644 index a0d059061..000000000 --- a/agent/agent/conn/conn.go +++ /dev/null @@ -1,63 +0,0 @@ -package conn - -import ( - "crypto/tls" - "fmt" - "time" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/utils" - grpc "google.golang.org/grpc" - "google.golang.org/grpc/credentials" -) - -const ( - maxMessageSize = 1024 * 1024 * 1024 - maxConnectionAttempts = 3 - initialReconnectDelay = 10 * time.Second - maxReconnectDelay = 60 * time.Second -) - -func ConnectToServer(cnf *configuration.Config, h *logger.Logger, addrs, port string) (*grpc.ClientConn, error) { - connectionAttemps := 0 - reconnectDelay := initialReconnectDelay - - // Connect to the gRPC server - serverAddress := addrs + ":" + port - var conn *grpc.ClientConn - var err error - - for { - if connectionAttemps >= maxConnectionAttempts { - return nil, fmt.Errorf("failed to connect to Server") - } - - h.Info("trying to connect to Server...") - var opts grpc.DialOption - if !cnf.SkipCertValidation { - creds, err := credentials.NewClientTLSFromFile(configuration.GetCaPath(), "") - if err != nil { - return nil, fmt.Errorf("failed to load CA trust certificate: %v", err) - } - opts = grpc.WithTransportCredentials(creds) - } else { - tlsConfig := &tls.Config{InsecureSkipVerify: true} - creds := credentials.NewTLS(tlsConfig) - opts = grpc.WithTransportCredentials(creds) - } - - conn, err = grpc.NewClient(serverAddress, opts, grpc.WithDefaultCallOptions(grpc.MaxCallRecvMsgSize(maxMessageSize))) - if err != nil { - connectionAttemps++ - h.Info("error connecting to Server, trying again in %.0f seconds", reconnectDelay.Seconds()) - time.Sleep(reconnectDelay) - reconnectDelay = utils.IncrementReconnectDelay(reconnectDelay, maxReconnectDelay) - continue - } - - break - } - - return conn, nil -} diff --git a/agent/agent/delete.go b/agent/agent/delete.go new file mode 100644 index 000000000..af51fca85 --- /dev/null +++ b/agent/agent/delete.go @@ -0,0 +1,44 @@ +package agent + +import ( + context "context" + "fmt" + "os/user" + "strconv" + + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/conn" + "github.com/utmstack/UTMStack/agent/utils" + "google.golang.org/grpc/metadata" +) + +func DeleteAgent(cnf *config.Config) error { + connection, err := conn.GetAgentManagerConnection(cnf) + if err != nil { + return fmt.Errorf("error connecting to Agent Manager: %v", err) + } + + agentClient := NewAgentServiceClient(connection) + ctx, cancel := context.WithCancel(context.Background()) + defer cancel() + ctx = metadata.AppendToOutgoingContext(ctx, "key", cnf.AgentKey) + ctx = metadata.AppendToOutgoingContext(ctx, "id", strconv.Itoa(int(cnf.AgentID))) + ctx = metadata.AppendToOutgoingContext(ctx, "type", "agent") + + currentUser, err := user.Current() + if err != nil { + return fmt.Errorf("error getting user: %v", err) + } + + delet := &AgentDelete{ + DeletedBy: currentUser.Username, + } + + _, err = agentClient.DeleteAgent(ctx, delet) + if err != nil { + utils.Logger.ErrorF("error removing UTMStack Agent from Agent Manager %v", err) + } + + utils.Logger.Info("UTMStack Agent removed successfully") + return nil +} diff --git a/agent/agent/filters/beats.go b/agent/agent/filters/beats.go deleted file mode 100644 index e0f351f46..000000000 --- a/agent/agent/filters/beats.go +++ /dev/null @@ -1,54 +0,0 @@ -package filters - -import ( - "regexp" - - "github.com/utmstack/UTMStack/agent/agent/configuration" -) - -var RegexspBeats = map[configuration.LogType]string{ - configuration.LogTypeApacheModule: `"type":"apache"|"module":"apache"`, - configuration.LogTypeLinuxAuditdModule: `"type":"auditd"|"module":"auditd"`, - configuration.LogTypeElasticsearchModule: `"type":"elasticsearch"|"module":"elasticsearch"`, - configuration.LogTypeKafkaModule: `"type":"kafka"|"module":"kafka"`, - configuration.LogTypeKibanaModule: `"type":"kibana"|"module":"kibana"`, - configuration.LogTypeLogstashModule: `"type":"logstash"|"module":"logstash"`, - configuration.LogTypeMongodbModule: `"type":"mongodb"|"module":"mongodb"`, - configuration.LogTypeMysqlModule: `"type":"mysql"|"module":"mysql"`, - configuration.LogTypeNginxModule: `"type":"nginx"|"module":"nginx"`, - configuration.LogTypeOsqueryModule: `"type":"osquery"|"module":"osquery"`, - configuration.LogTypePostgresqlModule: `"type":"postgresql"|"module":"postgresql"`, - configuration.LogTypeRedisModule: `"type":"redis"|"module":"redis"`, - configuration.LogTypeLinuxAgent: `"type":"system"|"module":"system"`, - configuration.LogTypeIisModule: `"type":"iis"|"module":"iis"`, - configuration.LogTypeTraefikModule: `"type":"traefik"|"module":"traefik"`, - configuration.LogTypeNatsModule: `"type":"nats"|"module":"nats"`, - configuration.LogTypeHaproxyModule: `"type":"haproxy"|"module":"haproxy"`, -} - -func indentifyBeatLogSource(log string) (configuration.LogType, error) { - for logType, regp := range RegexspBeats { - regExpCompiled, err := regexp.Compile(string(regp)) - if err != nil { - return "", err - } - if regExpCompiled.MatchString(log) { - return logType, nil - } - } - return configuration.LogTypeGeneric, nil -} - -func ProcessBeatData(logBatch []string) (map[string][]string, error) { - classifiedLogs := make(map[string][]string) - for _, log := range logBatch { - if logType, err := indentifyBeatLogSource(log); err != nil { - return nil, err - } else { - if logType != "" { - classifiedLogs[string(logType)] = append(classifiedLogs[string(logType)], log) - } - } - } - return classifiedLogs, nil -} diff --git a/agent/agent/filters/cisco.go b/agent/agent/filters/cisco.go deleted file mode 100644 index e2b9f65c4..000000000 --- a/agent/agent/filters/cisco.go +++ /dev/null @@ -1,38 +0,0 @@ -package filters - -import ( - "regexp" - - "github.com/utmstack/UTMStack/agent/agent/configuration" -) - -var RegexspCisco = map[configuration.LogType]string{ - configuration.LogTypeCiscoAsa: `%ASA-`, - configuration.LogTypeCiscoFirepower: `%FTD-`, - configuration.LogTypeCiscoSwitch: `%(\w|_)+-((\b\w+\b-\b\w+\b-)?)(\d)-([A-Z]|_)+`, -} - -func indentifyCiscoLogSource(log string) (configuration.LogType, error) { - for logType, regp := range RegexspCisco { - regExpCompiled, err := regexp.Compile(string(regp)) - if err != nil { - return "", err - } - if regExpCompiled.MatchString(log) { - return logType, nil - } - } - return configuration.LogTypeCiscoMeraki, nil -} - -func ProcessCiscoData(logBatch []string) (map[string][]string, error) { - classifiedLogs := make(map[string][]string) - for _, log := range logBatch { - if logType, err := indentifyCiscoLogSource(log); err != nil { - return nil, err - } else { - classifiedLogs[string(logType)] = append(classifiedLogs[string(logType)], log) - } - } - return classifiedLogs, nil -} diff --git a/agent/agent/incident_response.go b/agent/agent/incident_response.go new file mode 100644 index 000000000..77cec794e --- /dev/null +++ b/agent/agent/incident_response.go @@ -0,0 +1,132 @@ +package agent + +import ( + "context" + "runtime" + "strings" + "time" + + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/conn" + "github.com/utmstack/UTMStack/agent/utils" + codes "google.golang.org/grpc/codes" + status "google.golang.org/grpc/status" + "google.golang.org/protobuf/types/known/timestamppb" +) + +func IncidentResponseStream(cnf *config.Config, ctx context.Context) { + path := utils.GetMyPath() + var connErrMsgWritten, errorLogged bool + + for { + connection, err := conn.GetAgentManagerConnection(cnf) + if err != nil { + if !connErrMsgWritten { + utils.Logger.ErrorF("error connecting to Agent Manager: %v", err) + connErrMsgWritten = true + } + time.Sleep(timeToSleep) + continue + } + + client := NewAgentServiceClient(connection) + stream, err := client.AgentStream(ctx) + if err != nil { + if !connErrMsgWritten { + utils.Logger.ErrorF("failed to start AgentStream: %v", err) + connErrMsgWritten = true + } + time.Sleep(timeToSleep) + continue + } + + connErrMsgWritten = false + + for { + in, err := stream.Recv() + if err != nil { + if strings.Contains(err.Error(), "EOF") { + time.Sleep(timeToSleep) + break + } + st, ok := status.FromError(err) + if ok && (st.Code() == codes.Unavailable || st.Code() == codes.Canceled) { + if !errorLogged { + utils.Logger.ErrorF("error receiving command from server: %v", err) + errorLogged = true + } + time.Sleep(timeToSleep) + break + } else { + if !errorLogged { + utils.Logger.ErrorF("error receiving command from server: %v", err) + errorLogged = true + } + time.Sleep(timeToSleep) + continue + } + } + + switch msg := in.StreamMessage.(type) { + case *BidirectionalStream_Command: + err = commandProcessor(path, stream, cnf, []string{msg.Command.Command, in.GetCommand().CmdId}) + if err != nil { + if strings.Contains(err.Error(), "EOF") { + time.Sleep(timeToSleep) + break + } + st, ok := status.FromError(err) + if ok && (st.Code() == codes.Unavailable || st.Code() == codes.Canceled) { + if !errorLogged { + utils.Logger.ErrorF("error sending result to server: %v", err) + errorLogged = true + } + time.Sleep(timeToSleep) + break + } else { + if !errorLogged { + utils.Logger.ErrorF("error sending result to server: %v", err) + errorLogged = true + } + time.Sleep(timeToSleep) + continue + } + } + } + errorLogged = false + } + } +} + +func commandProcessor(path string, stream AgentService_AgentStreamClient, cnf *config.Config, commandPair []string) error { + var result string + var errB bool + + utils.Logger.Info("Received command: %s", commandPair[0]) + + switch runtime.GOOS { + case "windows": + result, errB = utils.ExecuteWithResult("cmd.exe", path, "/C", commandPair[0]) + case "linux": + result, errB = utils.ExecuteWithResult("sh", path, "-c", commandPair[0]) + default: + utils.Logger.Fatal("unsupported operating system: %s", runtime.GOOS) + } + + if errB { + utils.Logger.ErrorF("error executing command %s: %s", commandPair[0], result) + } else { + utils.Logger.Info("Result when executing the command %s: %s", commandPair[0], result) + } + + if err := stream.Send(&BidirectionalStream{ + StreamMessage: &BidirectionalStream_Result{ + Result: &CommandResult{Result: result, AgentKey: cnf.AgentKey, ExecutedAt: timestamppb.Now(), CmdId: commandPair[1]}, + }, + }); err != nil { + return err + } else { + utils.Logger.Info("Result sent to server successfully!!!") + } + return nil +} diff --git a/agent/agent/log-collector-config-sample.json b/agent/agent/log-collector-config-sample.json deleted file mode 100644 index 340e1e0ee..000000000 --- a/agent/agent/log-collector-config-sample.json +++ /dev/null @@ -1,71 +0,0 @@ -{ - "integrations": { - "syslog": { - "tcp_port": { "enabled": false, "value": "7014" }, - "udp_port": { "enabled": false, "value": "7014" } - }, - "antivirus_deceptivebytes": { - "tcp_port": { "enabled": false, "value": "7010" }, - "udp_port": { "enabled": false, "value": "7010" } - }, - "antivirus_eset": { - "tcp_port": { "enabled": false, "value": "7003" }, - "udp_port": { "enabled": false, "value": "7003" } - }, - "antivirus_kaspersky": { - "tcp_port": { "enabled": false, "value": "7004" }, - "udp_port": { "enabled": false, "value": "7004" } - }, - "antivirus_sentinel_one": { - "tcp_port": { "enabled": false, "value": "7012" }, - "udp_port": { "enabled": false, "value": "7012" } - }, - "cisco": { - "tcp_port": { "enabled": false, "value": "1470" }, - "udp_port": { "enabled": false, "value": "514" } - }, - "firewall_fortinet": { - "tcp_port": { "enabled": false, "value": "7005" }, - "udp_port": { "enabled": false, "value": "7005" } - }, - "firewall_mikrotik": { - "tcp_port": { "enabled": false, "value": "7007" }, - "udp_port": { "enabled": false, "value": "7007" } - }, - "firewall_paloalto": { - "tcp_port": { "enabled": false, "value": "7006" }, - "udp_port": { "enabled": false, "value": "7006" } - }, - "firewall_sonicwall": { - "tcp_port": { "enabled": false, "value": "7009" }, - "udp_port": { "enabled": false, "value": "7009" } - }, - "firewall_sophos": { - "tcp_port": { "enabled": false, "value": "7008" }, - "udp_port": { "enabled": false, "value": "7008" } - }, - "macos": { - "tcp_port": { "enabled": false, "value": "7015" }, - "udp_port": { "enabled": false, "value": "7015" } - }, - "vmware": { - "tcp_port": { "enabled": false, "value": "7002" }, - "udp_port": { "enabled": false, "value": "7002" } - }, - "netflow": { - "udp_port": { "enabled": false, "value": "2055" } - }, - "aix": { - "tcp_port": { "enabled": false, "value": "7016" }, - "udp_port": { "enabled": false, "value": "7016" } - }, - "firewall_pfsense": { - "tcp_port": { "enabled": false, "value": "7017" }, - "udp_port": { "enabled": false, "value": "7017" } - }, - "firewall_fortiweb": { - "tcp_port": { "enabled": false, "value": "7018" }, - "udp_port": { "enabled": false, "value": "7018" } - } - } -} \ No newline at end of file diff --git a/agent/agent/logservice/processor.go b/agent/agent/logservice/processor.go deleted file mode 100644 index 03c01cb02..000000000 --- a/agent/agent/logservice/processor.go +++ /dev/null @@ -1,189 +0,0 @@ -package logservice - -import ( - "bufio" - context "context" - "fmt" - "os" - "path/filepath" - "strings" - "sync" - "time" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/agent" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/utils" -) - -type LogProcessor struct { -} - -type LogPipe struct { - Src string - Logs []string -} - -var ( - processor LogProcessor - processorOnce sync.Once - LogQueue = make(chan LogPipe, 1000) - MinutesForCleanLog = 10080 // 7 days in minutes(7*24*60) - MinutesForReportLogsCounted = time.Duration(5 * time.Minute) -) - -func GetLogProcessor() LogProcessor { - processorOnce.Do(func() { - processor = LogProcessor{} - }) - return processor -} - -func (l *LogProcessor) ProcessLogs(client LogServiceClient, ctx context.Context, cnf *configuration.Config, h *logger.Logger) { - connectionTime := 0 * time.Second - reconnectDelay := configuration.InitialReconnectDelay - invalidKeyCounter := 0 - - logsProcessCounter := map[string]int{} - go func() { - for { - time.Sleep(MinutesForReportLogsCounted) - SaveCountedLogs(h, logsProcessCounter) - logsProcessCounter = map[string]int{} - } - }() - - for { - if connectionTime >= configuration.MaxConnectionTime { - connectionTime = 0 * time.Second - reconnectDelay = configuration.InitialReconnectDelay - continue - } - - newLog := <-LogQueue - rcv, err := client.ProcessLogs(ctx, &LogMessage{Type: agent.ConnectorType_AGENT, LogType: newLog.Src, Data: newLog.Logs}) - if err != nil { - h.ErrorF("Error sending logs to Log Auth Proxy: %v", err) - for _, log := range newLog.Logs { - h.ErrorF("log with errors: %s", log) - } - if strings.Contains(err.Error(), "invalid agent key") { - invalidKeyCounter++ - if invalidKeyCounter >= 20 { - h.Info("Uninstalling agent: reason: agent has been removed from the panel...") - err := agent.UninstallAll() - if err != nil { - h.ErrorF("Error uninstalling agent: %s", err) - } - } - } else { - invalidKeyCounter = 0 - } - - time.Sleep(reconnectDelay) - connectionTime = utils.IncrementReconnectTime(connectionTime, reconnectDelay, configuration.MaxConnectionTime) - reconnectDelay = utils.IncrementReconnectDelay(reconnectDelay, configuration.MaxReconnectDelay) - continue - } else if !rcv.Received { - h.ErrorF("Error sending logs to Log Auth Proxy: %s", rcv.Message) - h.Info("logs with errors: ") - for _, log := range newLog.Logs { - h.Info("log: %s", log) - } - if strings.Contains(rcv.Message, "invalid agent key") { - invalidKeyCounter++ - if invalidKeyCounter >= 20 { - h.Info("Uninstalling agent: reason: agent has been removed from the panel...") - err := agent.UninstallAll() - if err != nil { - h.ErrorF("Error uninstalling agent: %s", err) - } - } - } else { - invalidKeyCounter = 0 - } - - time.Sleep(reconnectDelay) - connectionTime = utils.IncrementReconnectTime(connectionTime, reconnectDelay, configuration.MaxConnectionTime) - reconnectDelay = utils.IncrementReconnectDelay(reconnectDelay, configuration.MaxReconnectDelay) - continue - } - - logsProcessCounter[newLog.Src] += len(newLog.Logs) - invalidKeyCounter = 0 - } -} - -func (l *LogProcessor) ProcessLogsWithHighPriority(msg string, client LogServiceClient, ctx context.Context, cnf *configuration.Config, h *logger.Logger) error { - host, err := os.Hostname() - if err != nil { - return fmt.Errorf("error getting hostname: %v", err) - } - - rcv, err := client.ProcessLogs(ctx, &LogMessage{Type: agent.ConnectorType_AGENT, LogType: string(configuration.LogTypeGeneric), Data: []string{configuration.GetMessageFormated(host, msg)}}) - if err != nil { - return fmt.Errorf("error sending logs to Log Auth Proxy: %v", err) - } - if !rcv.Received { - return fmt.Errorf("error sending logs to Log Auth Proxy: %s", rcv.Message) - } - return nil -} - -func SaveCountedLogs(h *logger.Logger, logsProcessCounter map[string]int) { - path, err := utils.GetMyPath() - if err != nil { - h.Fatal("Failed to get current path: %v", err) - } - - filePath := filepath.Join(path, "logs_process") - logFile := filepath.Join(filePath, "processed_logs.txt") - utils.CreatePathIfNotExist(filePath) - - file, err := os.OpenFile(logFile, os.O_RDWR|os.O_CREATE|os.O_APPEND, 0666) - if err != nil { - h.ErrorF("error opening processed_logs.txt file: %s", err) - return - } - defer file.Close() - - var firstLogTime time.Time - var firstLine string - scanner := bufio.NewScanner(file) - for scanner.Scan() { - firstLine = scanner.Text() - break - } - - if firstLine != "" { - firstLogTime, err = time.Parse("2006/01/02 15:04:05.9999999 -0700 MST", strings.Split(firstLine, " - ")[0]) - if err != nil { - h.ErrorF("error parsing first log time: %s", err) - return - } - - if !firstLogTime.IsZero() && time.Since(firstLogTime).Minutes() >= float64(MinutesForCleanLog) { - file.Close() - if err := os.Remove(logFile); err != nil { - h.ErrorF("error removing processed_logs.txt file: %s", err) - return - } - file, err = os.OpenFile(logFile, os.O_RDWR|os.O_CREATE|os.O_APPEND, 0666) - if err != nil { - h.ErrorF("error opening processed_logs.txt file: %s", err) - return - } - } - } - - for name, counter := range logsProcessCounter { - if counter > 0 { - _, err = file.WriteString(fmt.Sprintf("%v - %d logs from %s have been processed\n", time.Now().Format("2006/01/02 15:04:05.9999999 -0700 MST"), counter, name)) - if err != nil { - h.ErrorF("error writing to processed_logs.txt file: %s", err) - continue - } - } - } - -} diff --git a/agent/agent/main.go b/agent/agent/main.go deleted file mode 100644 index a0289ae5f..000000000 --- a/agent/agent/main.go +++ /dev/null @@ -1,176 +0,0 @@ -package main - -import ( - "context" - "fmt" - "log" - "os" - "path/filepath" - "time" - - pb "github.com/utmstack/UTMStack/agent/agent/agent" - "github.com/utmstack/UTMStack/agent/agent/beats" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/conn" - "github.com/utmstack/UTMStack/agent/agent/logservice" - "github.com/utmstack/UTMStack/agent/agent/modules" - "github.com/utmstack/UTMStack/agent/agent/serv" - "github.com/utmstack/UTMStack/agent/agent/utils" - "google.golang.org/grpc/metadata" -) - -func main() { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - log.Fatalf("Failed to get current path: %v", err) - } - - // Configuring log saving - var h = utils.CreateLogger(filepath.Join(path, "logs", configuration.SERV_LOG)) - - if len(os.Args) > 1 { - arg := os.Args[1] - switch arg { - case "run": - serv.RunService(h) - case "install": - h.Info("Installing UTMStack Agent service...") - - // Generate Certificates - certsPath := filepath.Join(path, "certs") - err = utils.CreatePathIfNotExist(certsPath) - if err != nil { - h.Fatal("error creating path: %s", err) - } - - err = utils.GenerateCerts(certsPath) - if err != nil { - h.Fatal("error generating certificates: %v", err) - } - - cnf, utmKey := configuration.GetInitialConfig() - - // Connect to Agent Manager - conn, err := conn.ConnectToServer(cnf, h, cnf.Server, configuration.AGENTMANAGERPORT) - if err != nil { - h.Fatal("error connecting to Agent Manager: %v", err) - } - defer conn.Close() - h.Info("Connection to Agent Manager successful!!!") - - // Register Agent - if err = pb.RegisterAgent(conn, cnf, utmKey, h); err != nil { - h.Fatal("%v", err) - } - - // Write config in config.yml - if err = configuration.SaveConfig(cnf); err != nil { - h.Fatal("error writing config file: %v", err) - } - - if err = modules.ConfigureCollectorFirstTime(); err != nil { - h.Fatal("error configuring syslog server: %v", err) - } - - // Install Beats - if err = beats.InstallBeats(*cnf, h); err != nil { - h.Fatal("error installing beats: %v", err) - } - - serv.InstallService(h) - h.Info("UTMStack Agent service installed correctly") - - case "send-log": - msg := os.Args[2] - logp := logservice.GetLogProcessor() - - // Read config - cnf, err := configuration.GetCurrentConfig() - if err != nil { - os.Exit(0) - } - - // Connect to log-auth-proxy - connLogServ, err := conn.ConnectToServer(cnf, h, cnf.Server, configuration.AUTHLOGSPORT) - if err != nil { - h.ErrorF("error connecting to Log Auth Proxy: %v", err) - } - defer connLogServ.Close() - - // Create a client for LogService - logClient := logservice.NewLogServiceClient(connLogServ) - ctxLog, cancelLog := context.WithCancel(context.Background()) - defer cancelLog() - ctxLog = metadata.AppendToOutgoingContext(ctxLog, "agent-key", cnf.AgentKey) - - err = logp.ProcessLogsWithHighPriority(msg, logClient, ctxLog, cnf, h) - if err != nil { - h.ErrorF("error sending High Priority Log to Log Auth Proxy: %v", err) - } - case "enable-integration", "disable-integration": - integration := os.Args[2] - proto := os.Args[3] - - port, err := modules.ChangeIntegrationStatus(integration, proto, (arg == "enable-integration")) - if err != nil { - fmt.Printf("error trying to %s: %v", arg, err) - h.ErrorF("error trying to %s: %v", arg, err) - os.Exit(0) - } - fmt.Printf("%s %s done correctly in port %s %s", arg, integration, port, proto) - time.Sleep(5 * time.Second) - - case "change-port": - integration := os.Args[2] - proto := os.Args[3] - port := os.Args[4] - - old, err := modules.ChangePort(integration, proto, port) - if err != nil { - fmt.Printf("error trying to change port: %v", err) - h.ErrorF("error trying to change port: %v", err) - os.Exit(0) - } - fmt.Printf("change port done correctly from %s to %s in %s for %s integration", old, port, proto, integration) - time.Sleep(5 * time.Second) - - case "uninstall": - h.Info("Uninstalling UTMStack Agent service...") - - // Read config - cnf, err := configuration.GetCurrentConfig() - if err != nil { - h.Fatal("error getting config: %v", err) - } - - // Connect to Agent Manager - conn, err := conn.ConnectToServer(cnf, h, cnf.Server, configuration.AGENTMANAGERPORT) - if err != nil { - h.ErrorF("error connecting to Agent Manager: %v", err) - } else { - h.Info("Connection to Agent Manager successful!!!") - - // Delete agent - if err = pb.DeleteAgent(conn, cnf, h); err != nil { - h.ErrorF("error deleting agent: %v", err) - } - } - defer conn.Close() - - // Uninstall Beats - if err = beats.UninstallBeats(h); err != nil { - h.Fatal("error uninstalling beats: %v", err) - } - os.Remove(filepath.Join(path, "config.yml")) - - serv.UninstallService(h) - h.Info("UTMStack Agent service uninstalled correctly") - os.Exit(0) - default: - fmt.Println("unknown option") - } - } else { - serv.RunService(h) - } -} diff --git a/agent/agent/modules/template.go b/agent/agent/modules/template.go deleted file mode 100644 index 2c41f0d1e..000000000 --- a/agent/agent/modules/template.go +++ /dev/null @@ -1,52 +0,0 @@ -package modules - -import ( - "fmt" - "os" - "strings" -) - -func WriteCollectorConfig(integrations map[string]Integration, filename string) error { - fileContent := "{\n \"integrations\": {\n" - for name, integration := range integrations { - fileContent += fmt.Sprintf(" \"%s\": {\n", name) - if integration.TCP.Port != "" { - fileContent += fmt.Sprintf(" \"tcp_port\": {\"enabled\": %t, \"value\": \"%s\"},\n", integration.TCP.IsListen, integration.TCP.Port) - } - if integration.UDP.Port != "" { - fileContent += fmt.Sprintf(" \"udp_port\": {\"enabled\": %t, \"value\": \"%s\"},\n", integration.UDP.IsListen, integration.UDP.Port) - } - if strings.HasSuffix(fileContent, ",\n") { - fileContent = fileContent[:len(fileContent)-2] + "\n" - } - fileContent += " },\n" - } - if strings.HasSuffix(fileContent, ",\n") { - fileContent = fileContent[:len(fileContent)-2] + "\n" - } - fileContent += " }\n}\n" - - err := os.WriteFile(filename, []byte(fileContent), 0644) - if err != nil { - return err - } - - return nil -} - -func WriteCollectorConfigFromModules(mod []Module, filename string) error { - integrations := make(map[string]Integration) - for _, m := range mod { - integrations[string(m.GetDataType())] = Integration{ - TCP: Port{ - IsListen: m.IsPortListen("tcp"), - Port: m.GetPort("tcp"), - }, - UDP: Port{ - IsListen: m.IsPortListen("udp"), - Port: m.GetPort("udp"), - }, - } - } - return WriteCollectorConfig(integrations, filename) -} diff --git a/agent/agent/parser/beats.go b/agent/agent/parser/beats.go deleted file mode 100644 index b10ac9ebd..000000000 --- a/agent/agent/parser/beats.go +++ /dev/null @@ -1,80 +0,0 @@ -package parser - -import ( - "fmt" - "regexp" - "sync" - - "github.com/threatwinds/logger" - "github.com/threatwinds/validations" - "github.com/utmstack/UTMStack/agent/agent/configuration" -) - -var ( - beatsParser = BeatsParser{} - beatsParserOnce sync.Once - RegexspBeats = map[configuration.LogType]string{ - configuration.LogTypeApacheModule: `"type":"apache"|"module":"apache"`, - configuration.LogTypeLinuxAuditdModule: `"type":"auditd"|"module":"auditd"`, - configuration.LogTypeElasticsearchModule: `"type":"elasticsearch"|"module":"elasticsearch"`, - configuration.LogTypeKafkaModule: `"type":"kafka"|"module":"kafka"`, - configuration.LogTypeKibanaModule: `"type":"kibana"|"module":"kibana"`, - configuration.LogTypeLogstashModule: `"type":"logstash"|"module":"logstash"`, - configuration.LogTypeMongodbModule: `"type":"mongodb"|"module":"mongodb"`, - configuration.LogTypeMysqlModule: `"type":"mysql"|"module":"mysql"`, - configuration.LogTypeNginxModule: `"type":"nginx"|"module":"nginx"`, - configuration.LogTypeOsqueryModule: `"type":"osquery"|"module":"osquery"`, - configuration.LogTypePostgresqlModule: `"type":"postgresql"|"module":"postgresql"`, - configuration.LogTypeRedisModule: `"type":"redis"|"module":"redis"`, - configuration.LogTypeLinuxAgent: `"type":"system"|"module":"system"`, - configuration.LogTypeIisModule: `"type":"iis"|"module":"iis"`, - configuration.LogTypeTraefikModule: `"type":"traefik"|"module":"traefik"`, - configuration.LogTypeNatsModule: `"type":"nats"|"module":"nats"`, - configuration.LogTypeHaproxyModule: `"type":"haproxy"|"module":"haproxy"`, - } -) - -type BeatsParser struct{} - -func GetBeatsParser() *BeatsParser { - beatsParserOnce.Do(func() { - beatsParser = BeatsParser{} - }) - return &beatsParser -} - -func (p *BeatsParser) IdentifySource(log string) (configuration.LogType, error) { - for logType, regp := range RegexspBeats { - regExpCompiled, err := regexp.Compile(string(regp)) - if err != nil { - return "", err - } - if regExpCompiled.MatchString(log) { - return logType, nil - } - } - return configuration.LogTypeGeneric, nil -} - -func (p *BeatsParser) ProcessData(logBatch interface{}, h *logger.Logger) (map[string][]string, error) { - classifiedLogs := make(map[string][]string) - batch, ok := logBatch.([]string) - if !ok { - return nil, fmt.Errorf("invalid log batch type") - } - for _, log := range batch { - if logType, err := p.IdentifySource(log); err != nil { - return nil, err - } else { - if logType != "" { - validatedLog, _, err := validations.ValidateString(log, false) - if err != nil { - h.ErrorF("error validating log: %s: %v", log, err) - continue - } - classifiedLogs[string(logType)] = append(classifiedLogs[string(logType)], validatedLog) - } - } - } - return classifiedLogs, nil -} diff --git a/agent/agent/agent/ping.pb.go b/agent/agent/ping.pb.go similarity index 100% rename from agent/agent/agent/ping.pb.go rename to agent/agent/ping.pb.go diff --git a/agent/agent/agent/ping_grpc.pb.go b/agent/agent/ping_grpc.pb.go similarity index 100% rename from agent/agent/agent/ping_grpc.pb.go rename to agent/agent/ping_grpc.pb.go diff --git a/agent/agent/ping_imp.go b/agent/agent/ping_imp.go new file mode 100644 index 000000000..4dea548ef --- /dev/null +++ b/agent/agent/ping_imp.go @@ -0,0 +1,79 @@ +package agent + +import ( + "context" + "strings" + "time" + + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/conn" + "github.com/utmstack/UTMStack/agent/utils" + codes "google.golang.org/grpc/codes" + status "google.golang.org/grpc/status" +) + +var ( + timeToSleep = 10 * time.Second + pingInterval = 15 * time.Second +) + +func StartPing(cnf *config.Config, ctx context.Context) { + var connErrMsgWritten, errorLogged bool + + for { + connection, err := conn.GetAgentManagerConnection(cnf) + if err != nil { + if !connErrMsgWritten { + utils.Logger.ErrorF("error connecting to Agent Manager: %v", err) + connErrMsgWritten = true + } + time.Sleep(timeToSleep) + continue + } + + client := NewPingServiceClient(connection) + stream, err := client.Ping(ctx) + if err != nil { + if !connErrMsgWritten { + utils.Logger.ErrorF("failed to start Ping Stream: %v", err) + connErrMsgWritten = true + } + time.Sleep(timeToSleep) + continue + } + + connErrMsgWritten = false + + ticker := time.NewTicker(pingInterval) + + for range ticker.C { + err := stream.Send(&PingRequest{Type: ConnectorType_AGENT}) + if err != nil { + if strings.Contains(err.Error(), "EOF") { + time.Sleep(timeToSleep) + break + } + st, ok := status.FromError(err) + if ok && (st.Code() == codes.Unavailable || st.Code() == codes.Canceled) { + if !errorLogged { + utils.Logger.ErrorF("error sending Ping request: %v", err) + errorLogged = true + } + time.Sleep(timeToSleep) + break + } else { + if !errorLogged { + utils.Logger.ErrorF("error sending Ping request: %v", err) + errorLogged = true + } + time.Sleep(timeToSleep) + continue + } + } + + errorLogged = false + } + + ticker.Stop() + } +} diff --git a/agent/agent/protos/agent_config.proto b/agent/agent/protos/agent_config.proto deleted file mode 100644 index b824c5dd4..000000000 --- a/agent/agent/protos/agent_config.proto +++ /dev/null @@ -1,55 +0,0 @@ -syntax = "proto3"; - -option go_package = "github.com/utmstack/UTMStack/agent-manager/agent"; - -package agent; - -service AgentConfigService { - rpc GetAgentConfig(ListAgentsModulesRequest) returns (ListAgentsModulesResponse) {} - rpc AgentModuleUpdateStream(stream AgentModuleConfiguration) returns (stream UpdateConfigResponse) {} -} - -message AgentModule { - uint32 id = 1; - uint32 agent_id = 2; - string short_name = 3; - string large_name = 4; - string description = 5; - bool enabled = 6; - bool allow_disabled = 7; - repeated AgentModuleConfiguration module_configs = 8; -} - -message UpdateAgentModule { - string agent_module_short = 1; - string conf_key = 4; - string conf_value = 5; -} - -message AgentModuleConfiguration { - uint32 id = 1; - uint32 agent_module_id = 2; - string short_name = 3; - string conf_key = 4; - string conf_value = 5; - string conf_name = 6; - string conf_description = 7; - string conf_datatype = 8; - bool conf_required = 9; - string conf_regex = 10; -} - -message UpdateConfigResponse{ - string accepted = 1; -} - -// ListAgentsRequest message definition -message ListAgentsModulesRequest { - string agent_key = 2; -} - -// ListAgentsResponse message definition -message ListAgentsModulesResponse { - repeated AgentModule modules = 1; -} - diff --git a/agent/agent/protos/agent_malware.proto b/agent/agent/protos/agent_malware.proto deleted file mode 100644 index 8fc630bec..000000000 --- a/agent/agent/protos/agent_malware.proto +++ /dev/null @@ -1,91 +0,0 @@ -syntax = "proto3"; - -option go_package = "github.com/utmstack/UTMStack/agent-manager/agent"; - -package agent; - -service AgentMalwareService { - rpc GetAgentExclusions(ListExclusionRequest) returns (ListExclusionResponse) {} - rpc CreateNewMalwareEntry(stream AgentMalwareDetection) returns (stream AgentMalwareDetection) {} - rpc ChangeMalwareStatus(stream ChangeStatusRequest) returns (stream AgentMalwareDetection) {} - rpc ListAgentMalware(ListMalwareRequest) returns (ListMalwareResponse) {} - rpc ListAgentMalwareHistory(ListMalwareHistoryRequest) returns (ListMalwareHistoryResponse) {} -} - - -message ListExclusionResponse { - repeated AgentMalwareExclusion exclusions = 1; -} - -message ListExclusionRequest { - int64 agent_id = 1; -} - -message ChangeStatusRequest { - string malware_id = 1; - MalwareStatus status = 2; -} - -enum MalwareStatus { - NEW = 0; - DELETED = 1; - EXCLUDED = 2; - RESTORED = 3; -} - -message AgentMalwareDetection { - int64 id = 1; - uint32 agent_id = 2; - string file_path = 3; - string sha256 = 4; - string md5 = 5; - string description = 6; - MalwareStatus status = 7; -} - -message AgentMalwareHistory { - int64 id = 1; - uint32 malware_id = 2; - MalwareStatus prev_status = 3; - MalwareStatus to_status = 4; - string changed_by = 5; -} - -message AgentMalwareExclusion { - int64 id = 1; - string exclude_file_path = 2; - string excluded_by = 3; - string exclude_description = 4; - int64 agent_id = 5; -} - -// ListAgentsRequest message definition -message ListMalwareRequest { - int32 page_number = 1; - int32 page_size = 2; - string search_query = 3; - repeated string sort_by = 4; - bool sort_descending = 5; -} - -// ListAgentsResponse message definition -message ListMalwareResponse { - repeated AgentMalwareDetection malware = 1; - int32 total_pages = 2; - int32 total_results = 3; -} - -message ListMalwareHistoryRequest { - int32 page_number = 1; - int32 page_size = 2; - string search_query = 3; - repeated string sort_by = 4; - bool sort_descending = 5; -} - -// ListAgentsResponse message definition -message ListMalwareHistoryResponse { - repeated AgentMalwareHistory malware = 1; - int32 total_pages = 2; - int32 total_results = 3; -} \ No newline at end of file diff --git a/agent/agent/redline/redline.go b/agent/agent/redline/redline.go deleted file mode 100644 index 6cac121a3..000000000 --- a/agent/agent/redline/redline.go +++ /dev/null @@ -1,56 +0,0 @@ -package redline - -import ( - "fmt" - "path/filepath" - "time" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/utils" -) - -func CheckRedlineService(h *logger.Logger) { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - h.Fatal("Failed to get current path: %v", err) - } - - bin := configuration.GetAgentBin() - - time.Sleep(5 * time.Minute) - attempts := 0 - for { - if attempts >= 3 { - h.Info("Redline service has been stopped") - if err := utils.Execute(filepath.Join(path, bin), path, "send-log", fmt.Sprintf("%s service has been stopped", configuration.RedlineServName)); err != nil { - h.ErrorF("error checking %s: error sending log : %v", configuration.RedlineServName, err) - time.Sleep(time.Second * 5) - continue - } - if err := utils.RestartService(configuration.RedlineServName); err != nil { - h.ErrorF("error restarting %s service: %v", configuration.RedlineServName, err) - time.Sleep(time.Second * 5) - continue - } - - h.Info("%s restarted correctly", configuration.RedlineServName) - time.Sleep(time.Second * 5) - attempts = 0 - continue - } - - if isRunning, err := utils.CheckIfServiceIsActive(configuration.RedlineServName); err != nil { - h.ErrorF("error checking if %s is running: %v", configuration.RedlineServName, err) - time.Sleep(time.Second * 5) - } else if isRunning { - time.Sleep(time.Second * 5) - continue - } - if !utils.CheckIfPathExist(filepath.Join(path, "locks", configuration.RedlineLockName)) { - attempts++ - time.Sleep(time.Second * 30) - } - } -} diff --git a/agent/agent/agent/register.go b/agent/agent/register.go similarity index 57% rename from agent/agent/agent/register.go rename to agent/agent/register.go index 3b4f5f7d6..b69de591e 100644 --- a/agent/agent/agent/register.go +++ b/agent/agent/register.go @@ -3,22 +3,25 @@ package agent import ( context "context" "fmt" - "strings" - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/utils" - "google.golang.org/grpc" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/conn" + "github.com/utmstack/UTMStack/agent/models" + "github.com/utmstack/UTMStack/agent/utils" "google.golang.org/grpc/metadata" ) -func RegisterAgent(conn *grpc.ClientConn, cnf *configuration.Config, UTMKey string, h *logger.Logger) error { - // Create a client for AgentService - agentClient := NewAgentServiceClient(conn) +func RegisterAgent(cnf *config.Config, UTMKey string) error { + connection, err := conn.GetAgentManagerConnection(cnf) + if err != nil { + return fmt.Errorf("error connecting to Agent Manager: %v", err) + } + + agentClient := NewAgentServiceClient(connection) ctx, cancel := context.WithCancel(context.Background()) + ctx = metadata.AppendToOutgoingContext(ctx, "connection-key", UTMKey) defer cancel() - // Register the agent and store the result in a file ip, err := utils.GetIPAddress() if err != nil { return err @@ -29,9 +32,10 @@ func RegisterAgent(conn *grpc.ClientConn, cnf *configuration.Config, UTMKey stri return fmt.Errorf("error getting os info: %v", err) } - version, err := GetVersion() + version := models.Version{} + err = utils.ReadJson(config.VersionPath, &version) if err != nil { - return fmt.Errorf("error getting agent version: %v", err) + return fmt.Errorf("error reading version file: %v", err) } request := &AgentRequest{ @@ -39,7 +43,7 @@ func RegisterAgent(conn *grpc.ClientConn, cnf *configuration.Config, UTMKey stri Hostname: osInfo.Hostname, Os: osInfo.OsType, Platform: osInfo.Platform, - Version: version, + Version: version.Version, RegisterBy: osInfo.CurrentUser, Mac: osInfo.Mac, OsMajorVersion: osInfo.OsMajorVersion, @@ -48,19 +52,13 @@ func RegisterAgent(conn *grpc.ClientConn, cnf *configuration.Config, UTMKey stri Addresses: osInfo.Addresses, } - ctx = metadata.AppendToOutgoingContext(ctx, "connection-key", UTMKey) response, err := agentClient.RegisterAgent(ctx, request) if err != nil { - if strings.Contains(err.Error(), "hostname has already been registered") { - return fmt.Errorf("failed to register agent: hostname has already been registered") - } return fmt.Errorf("failed to register agent: %v", err) } cnf.AgentID = uint(response.Id) cnf.AgentKey = response.Key - h.Info("successfully registered agent") - return nil } diff --git a/agent/agent/serv/run.go b/agent/agent/serv/run.go deleted file mode 100644 index 1706b223a..000000000 --- a/agent/agent/serv/run.go +++ /dev/null @@ -1,19 +0,0 @@ -package serv - -import ( - "github.com/kardianos/service" - "github.com/threatwinds/logger" -) - -func RunService(h *logger.Logger) { - svcConfig := GetConfigServ() - prg := new(program) - newService, err := service.New(prg, svcConfig) - if err != nil { - h.Fatal("error creating new service: %v", err) - } - err = newService.Run() - if err != nil { - h.Fatal("error running new service: %v", err) - } -} diff --git a/agent/agent/serv/service.go b/agent/agent/serv/service.go deleted file mode 100644 index 7b2278833..000000000 --- a/agent/agent/serv/service.go +++ /dev/null @@ -1,101 +0,0 @@ -package serv - -import ( - "context" - "log" - "os" - "os/signal" - "path/filepath" - "strconv" - "syscall" - - "github.com/kardianos/service" - pb "github.com/utmstack/UTMStack/agent/agent/agent" - "github.com/utmstack/UTMStack/agent/agent/beats" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/conn" - "github.com/utmstack/UTMStack/agent/agent/logservice" - "github.com/utmstack/UTMStack/agent/agent/modules" - "github.com/utmstack/UTMStack/agent/agent/redline" - "github.com/utmstack/UTMStack/agent/agent/utils" - "google.golang.org/grpc/metadata" -) - -type program struct{} - -func (p *program) Start(s service.Service) error { - go p.run() - return nil -} - -func (p *program) Stop(s service.Service) error { - return nil -} - -func (p *program) run() { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - log.Fatalf("Failed to get current path: %v", err) - } - - // Configuring log saving - var h = utils.CreateLogger(filepath.Join(path, "logs", configuration.SERV_LOG)) - // Read config - cnf, err := configuration.GetCurrentConfig() - if err != nil { - h.Fatal("error getting config: %v", err) - } - - // Connect to Agent Manager - connAgentmanager, err := conn.ConnectToServer(cnf, h, cnf.Server, configuration.AGENTMANAGERPORT) - if err != nil { - h.Fatal("error connecting to Agent Manager: %v", err) - } - defer connAgentmanager.Close() - h.Info("Connection to Agent Manager successful!!!") - - // Connect to log-auth-proxy - connLogServ, err := conn.ConnectToServer(cnf, h, cnf.Server, configuration.AUTHLOGSPORT) - if err != nil { - h.Fatal("error connecting to Log Auth Proxy: %v", err) - } - defer connLogServ.Close() - h.Info("Connection to Log Auth Proxy successful!!!") - - // Create a client for AgentService - agentClient := pb.NewAgentServiceClient(connAgentmanager) - ctxAgent, cancelAgent := context.WithCancel(context.Background()) - defer cancelAgent() - ctxAgent = metadata.AppendToOutgoingContext(ctxAgent, "key", cnf.AgentKey) - ctxAgent = metadata.AppendToOutgoingContext(ctxAgent, "id", strconv.Itoa(int(cnf.AgentID))) - - // Create a client for PingService - pingClient := pb.NewPingServiceClient(connAgentmanager) - ctxPing, cancelPing := context.WithCancel(context.Background()) - defer cancelPing() - ctxPing = metadata.AppendToOutgoingContext(ctxPing, "key", cnf.AgentKey) - ctxPing = metadata.AppendToOutgoingContext(ctxPing, "id", strconv.Itoa(int(cnf.AgentID))) - - // Create a client for LogService - logClient := logservice.NewLogServiceClient(connLogServ) - ctxLog, cancelLog := context.WithCancel(context.Background()) - defer cancelLog() - ctxLog = metadata.AppendToOutgoingContext(ctxLog, "key", cnf.AgentKey) - ctxLog = metadata.AppendToOutgoingContext(ctxLog, "id", strconv.Itoa(int(cnf.AgentID))) - - logp := logservice.GetLogProcessor() - go logp.ProcessLogs(logClient, ctxLog, cnf, h) - - beats.BeatsLogsReader(h) - go redline.CheckRedlineService(h) - - go pb.UpdateAgent(agentClient, ctxAgent) - go modules.ModulesUp(h) - go pb.StartPing(pingClient, ctxPing, cnf, h) - go pb.IncidentResponseStream(agentClient, ctxAgent, cnf, h) - - signals := make(chan os.Signal, 1) - signal.Notify(signals, syscall.SIGINT, syscall.SIGTERM) - <-signals -} diff --git a/agent/agent/serv/uninstall.go b/agent/agent/serv/uninstall.go deleted file mode 100644 index fe9d6edcd..000000000 --- a/agent/agent/serv/uninstall.go +++ /dev/null @@ -1,18 +0,0 @@ -package serv - -import ( - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/utils" -) - -func UninstallService(h *logger.Logger) { - // Uninstall service - err := utils.StopService("UTMStackAgent") - if err != nil { - h.Fatal("error stopping UTMStackAgent: %v", err) - } - err = utils.UninstallService("UTMStackAgent") - if err != nil { - h.Fatal("error uninstalling UTMStackAgent: %v", err) - } -} diff --git a/agent/agent/uninstall.go b/agent/agent/uninstall.go new file mode 100644 index 000000000..3d0bbf291 --- /dev/null +++ b/agent/agent/uninstall.go @@ -0,0 +1,17 @@ +package agent + +import ( + "fmt" + "path/filepath" + + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/utils" +) + +func UninstallAll() error { + err := utils.Execute(filepath.Join(utils.GetMyPath(), fmt.Sprintf(config.ServiceFile, "")), utils.GetMyPath(), "uninstall") + if err != nil { + return fmt.Errorf("%v", err) + } + return nil +} diff --git a/agent/agent/update.go b/agent/agent/update.go new file mode 100644 index 000000000..7fca7450e --- /dev/null +++ b/agent/agent/update.go @@ -0,0 +1,48 @@ +package agent + +import ( + context "context" + "fmt" + + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/conn" + "github.com/utmstack/UTMStack/agent/models" + "github.com/utmstack/UTMStack/agent/utils" +) + +func UpdateAgent(cnf *config.Config, ctx context.Context) error { + connection, err := conn.GetAgentManagerConnection(cnf) + if err != nil { + return fmt.Errorf("error connecting to Agent Manager: %v", err) + } + + client := NewAgentServiceClient(connection) + + osInfo, err := utils.GetOsInfo() + if err != nil { + return fmt.Errorf("error getting os info: %v", err) + } + + version := models.Version{} + err = utils.ReadJson(config.VersionPath, &version) + if err != nil { + utils.Logger.Fatal("error reading version file: %v", err) + } + + request := &AgentRequest{ + Hostname: osInfo.Hostname, + Version: version.Version, + Mac: osInfo.Mac, + OsMajorVersion: osInfo.OsMajorVersion, + OsMinorVersion: osInfo.OsMinorVersion, + Aliases: osInfo.Aliases, + Addresses: osInfo.Addresses, + } + + _, err = client.UpdateAgent(ctx, request) + if err != nil { + return fmt.Errorf("error updating agent: %v", err) + } + + return nil +} diff --git a/agent/agent/utils/logger.go b/agent/agent/utils/logger.go deleted file mode 100644 index 213f64a69..000000000 --- a/agent/agent/utils/logger.go +++ /dev/null @@ -1,22 +0,0 @@ -package utils - -import ( - "sync" - - "github.com/threatwinds/logger" -) - -var ( - agentLogger *logger.Logger - loggerOnceInstance sync.Once -) - -// CreateLogger returns a single instance of a Logger configured to save logs to a rotating file. -func CreateLogger(filename string) *logger.Logger { - loggerOnceInstance.Do(func() { - agentLogger = logger.NewLogger( - &logger.Config{Format: "text", Level: 100, Output: filename, Retries: 3, Wait: 5}, - ) - }) - return agentLogger -} diff --git a/agent/agent/utils/services.go b/agent/agent/utils/services.go deleted file mode 100644 index b9fe53ab0..000000000 --- a/agent/agent/utils/services.go +++ /dev/null @@ -1,184 +0,0 @@ -package utils - -import ( - "fmt" - "os" - "runtime" - "strings" -) - -// CheckIfServiceIsActive checks if a service is active or running -func CheckIfServiceIsActive(serv string) (bool, error) { - var errB bool - var output string - - path, err := GetMyPath() - if err != nil { - return false, fmt.Errorf("error getting current path: %v", err) - } - - switch runtime.GOOS { - case "windows": - output, errB = ExecuteWithResult("sc", path, "query", serv) - case "linux": - output, errB = ExecuteWithResult("systemctl", path, "is-active", serv) - default: - return false, fmt.Errorf("unknown operating system") - } - - if errB { - return false, nil - } - - serviceStatus := strings.ToLower(strings.TrimSpace(string(output))) - if runtime.GOOS == "linux" { - return serviceStatus == "active", nil - } else if runtime.GOOS == "windows" { - return strings.Contains(serviceStatus, "running"), nil - } - - return false, fmt.Errorf("unsupported operating system") -} - -// RestartService restarts a service -func RestartService(serv string) error { - path, err := GetMyPath() - if err != nil { - return fmt.Errorf("error getting current path: %v", err) - } - - isRunning, err := CheckIfServiceIsActive(serv) - if err != nil { - return fmt.Errorf("error checking if %s service is active: %v", serv, err) - } - - switch runtime.GOOS { - case "windows": - if isRunning { - err := Execute("sc", path, "stop", serv) - if err != nil { - return fmt.Errorf("error stopping service: %v", err) - } - } - err := Execute("sc", path, "start", serv) - if err != nil { - return fmt.Errorf("error starting service: %v", err) - } - - case "linux": - if isRunning { - err := Execute("systemctl", path, "restart", serv) - if err != nil { - return fmt.Errorf("error restarting service: %v", err) - } - } else { - err := Execute("systemctl", path, "start", serv) - if err != nil { - return fmt.Errorf("error starting service: %v", err) - } - } - } - return nil -} - -func StopService(name string) error { - path, err := GetMyPath() - if err != nil { - return err - } - switch runtime.GOOS { - case "windows": - err := Execute("sc", path, "stop", name) - if err != nil { - return fmt.Errorf("error stoping service: %v", err) - } - case "linux": - err := Execute("systemctl", path, "stop", name) - if err != nil { - return fmt.Errorf("error stoping service: %v", err) - } - } - return nil -} - -func UninstallService(name string) error { - path, err := GetMyPath() - if err != nil { - return err - } - switch runtime.GOOS { - case "windows": - err := Execute("sc", path, "delete", name) - if err != nil { - return fmt.Errorf("error uninstalling service: %v", err) - } - case "linux": - err := Execute("systemctl", path, "disable", name) - if err != nil { - return fmt.Errorf("error uninstalling service: %v", err) - } - err = Execute("rm", "/etc/systemd/system/", "/etc/systemd/system/"+name+".service") - if err != nil { - return fmt.Errorf("error uninstalling service: %v", err) - } - } - return nil -} - -// CheckIfServiceIsInstalled checks if a service is installed -func CheckIfServiceIsInstalled(serv string) (bool, error) { - path, err := GetMyPath() - if err != nil { - return false, err - } - switch runtime.GOOS { - case "windows": - err = Execute("sc", path, "query", serv) - case "linux": - err = Execute("systemctl", path, "status", serv) - default: - return false, fmt.Errorf("operative system unknown") - } - - if err != nil { - return false, nil - } - return true, nil -} - -func CreateLinuxService(serviceName string, execStart string) error { - servicePath := "/etc/systemd/system/" + serviceName + ".service" - if !CheckIfPathExist(servicePath) { - file, err := os.Create(servicePath) - if err != nil { - return fmt.Errorf("error creating %s file: %v", servicePath, err) - } - defer file.Close() - - serviceContent := fmt.Sprintf(`[Unit] -Description=%s -After=network.target - -[Service] -ExecStart=%s -Restart=always - -[Install] -WantedBy=multi-user.target -`, serviceName, execStart) - - _, err = file.WriteString(serviceContent) - if err != nil { - return err - } - - err = file.Sync() - if err != nil { - return err - } - } else { - return fmt.Errorf("service %s already exists", serviceName) - } - - return nil -} diff --git a/agent/collectors/collectors.go b/agent/collectors/collectors.go new file mode 100644 index 000000000..865a5df6a --- /dev/null +++ b/agent/collectors/collectors.go @@ -0,0 +1,68 @@ +package collectors + +import ( + "fmt" + "runtime" + + "github.com/utmstack/UTMStack/agent/utils" +) + +type CollectorConfig struct { + LogsPath string + LogFileName string +} + +type Collector interface { + Install() error + SendSystemLogs() + Uninstall() error +} + +func getCollectorsInstances() []Collector { + var collectors []Collector + switch runtime.GOOS { + case "windows": + collectors = append(collectors, Winlogbeat{}) + collectors = append(collectors, Filebeat{}) + case "linux": + collectors = append(collectors, Filebeat{}) + } + + return collectors +} + +func InstallCollectors() error { + collectors := getCollectorsInstances() + + for _, collector := range collectors { + err := collector.Install() + if err != nil { + return fmt.Errorf("%v", err) + } + } + + utils.Logger.Info("collector installed correctly") + + return nil +} + +func LogsReader() { + collectors := getCollectorsInstances() + for _, collector := range collectors { + go collector.SendSystemLogs() + } +} + +func UninstallCollectors() error { + collectors := getCollectorsInstances() + + for _, collector := range collectors { + err := collector.Uninstall() + if err != nil { + return fmt.Errorf("%v", err) + } + } + + utils.Logger.Info("collectors uninstalled correctly") + return nil +} diff --git a/agent/agent/beats/filebeat.go b/agent/collectors/filebeat.go similarity index 64% rename from agent/agent/beats/filebeat.go rename to agent/collectors/filebeat.go index ebea2d4c8..6bca22e12 100644 --- a/agent/agent/beats/filebeat.go +++ b/agent/collectors/filebeat.go @@ -1,33 +1,29 @@ -package beats +package collectors import ( "fmt" "path/filepath" "runtime" - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/logservice" - "github.com/utmstack/UTMStack/agent/agent/parser" - "github.com/utmstack/UTMStack/agent/agent/utils" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/logservice" + "github.com/utmstack/UTMStack/agent/parser" + "github.com/utmstack/UTMStack/agent/utils" ) type Filebeat struct{} func (f Filebeat) Install() error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("error getting current path: %v", err) - } + path := utils.GetMyPath() filebLogPath := filepath.Join(path, "beats", "filebeat") - beatConfig := BeatConfig{ + beatConfig := CollectorConfig{ LogsPath: filepath.Join(filebLogPath, "logs"), LogFileName: "modulescollector", } - if isInstalled, err := utils.CheckIfServiceIsInstalled(configuration.ModulesServName); err != nil { - return fmt.Errorf("error checking if %s service is installed: %v", configuration.ModulesServName, err) + if isInstalled, err := utils.CheckIfServiceIsInstalled(config.ModulesServName); err != nil { + return fmt.Errorf("error checking if %s service is installed: %v", config.ModulesServName, err) } else if !isInstalled { if err = utils.CreatePathIfNotExist(beatConfig.LogsPath); err != nil { return fmt.Errorf("error creating %s folder", beatConfig.LogsPath) @@ -43,23 +39,23 @@ func (f Filebeat) Install() error { err = utils.Execute("sc", filebLogPath, "create", - configuration.ModulesServName, + config.ModulesServName, "binPath=", fmt.Sprintf("\"%s\\filebeat.exe\" --environment=windows_service -c \"%s\\filebeat.yml\" --path.home \"%s\" --path.data \"C:\\ProgramData\\filebeat\" --path.logs \"C:\\ProgramData\\filebeat\\logs\" -E logging.files.redirect_stderr=true", filebLogPath, filebLogPath, filebLogPath), "DisplayName=", - configuration.ModulesServName, + config.ModulesServName, "start=", "auto") if err != nil { - return fmt.Errorf("error installing %s service: %s", configuration.ModulesServName, err) + return fmt.Errorf("error installing %s service: %s", config.ModulesServName, err) } - err = utils.Execute("sc", filebLogPath, "start", configuration.ModulesServName) + err = utils.Execute("sc", filebLogPath, "start", config.ModulesServName) if err != nil { - return fmt.Errorf("error starting %s service: %s", configuration.ModulesServName, err) + return fmt.Errorf("error starting %s service: %s", config.ModulesServName, err) } case "linux": - if err = utils.CreateLinuxService(configuration.ModulesServName, fmt.Sprintf( + if err = utils.CreateLinuxService(config.ModulesServName, fmt.Sprintf( "%s -c %s -path.home %s -path.config %s -path.data /var/lib/filebeat -path.logs /var/log/filebeat", filepath.Join(filebLogPath, "filebeat"), filepath.Join(filebLogPath, "filebeat.yml"), @@ -67,7 +63,7 @@ func (f Filebeat) Install() error { filebLogPath, ), ); err != nil { - return fmt.Errorf("error creating %s service: %v", configuration.ModulesServName, err) + return fmt.Errorf("error creating %s service: %v", config.ModulesServName, err) } if err = utils.Execute("chmod", filebLogPath, "-R", "777", "filebeat"); err != nil { @@ -84,12 +80,12 @@ func (f Filebeat) Install() error { } if family == "debian" || family == "rhel" { - err := utils.Execute("systemctl", filebLogPath, "enable", configuration.ModulesServName) + err := utils.Execute("systemctl", filebLogPath, "enable", config.ModulesServName) if err != nil { return fmt.Errorf("%s", err) } - err = utils.Execute("systemctl", filebLogPath, "start", configuration.ModulesServName) + err = utils.Execute("systemctl", filebLogPath, "start", config.ModulesServName) if err != nil { return fmt.Errorf("%s", err) } @@ -104,7 +100,7 @@ func (f Filebeat) Install() error { return fmt.Errorf("%s", err) } - err = utils.Execute("systemctl", filebLogPath, "restart", configuration.ModulesServName) + err = utils.Execute("systemctl", filebLogPath, "restart", config.ModulesServName) if err != nil { return fmt.Errorf("%s", err) } @@ -115,21 +111,18 @@ func (f Filebeat) Install() error { return nil } -func (f Filebeat) SendSystemLogs(h *logger.Logger) { +func (f Filebeat) SendSystemLogs() { logLinesChan := make(chan []string) - path, err := utils.GetMyPath() - if err != nil { - h.ErrorF("error getting current path: %v", err) - } + path := utils.GetMyPath() filebLogPath := filepath.Join(path, "beats", "filebeat", "logs") parser := parser.GetParser("beats") - go utils.WatchFolder("modulescollector", filebLogPath, logLinesChan, configuration.BatchCapacity, h) + go utils.WatchFolder("modulescollector", filebLogPath, logLinesChan, config.BatchCapacity) for logLine := range logLinesChan { - beatsData, err := parser.ProcessData(logLine, h) + beatsData, err := parser.ProcessData(logLine) if err != nil { - h.ErrorF("error processing beats data: %v", err) + utils.Logger.ErrorF("error processing beats data: %v", err) continue } for typ, logB := range beatsData { @@ -142,17 +135,17 @@ func (f Filebeat) SendSystemLogs(h *logger.Logger) { } func (f Filebeat) Uninstall() error { - if isInstalled, err := utils.CheckIfServiceIsInstalled(configuration.ModulesServName); err != nil { - return fmt.Errorf("error checking if %s is running: %v", configuration.ModulesServName, err) + if isInstalled, err := utils.CheckIfServiceIsInstalled(config.ModulesServName); err != nil { + return fmt.Errorf("error checking if %s is running: %v", config.ModulesServName, err) } else if isInstalled { - err = utils.StopService(configuration.ModulesServName) + err = utils.StopService(config.ModulesServName) if err != nil { - return fmt.Errorf("error stopping %s: %v", configuration.ModulesServName, err) + return fmt.Errorf("error stopping %s: %v", config.ModulesServName, err) } - err = utils.UninstallService(configuration.ModulesServName) + err = utils.UninstallService(config.ModulesServName) if err != nil { - return fmt.Errorf("error uninstalling %s: %v", configuration.ModulesServName, err) + return fmt.Errorf("error uninstalling %s: %v", config.ModulesServName, err) } } return nil diff --git a/agent/agent/beats/winlogbeat.go b/agent/collectors/winlogbeat.go similarity index 57% rename from agent/agent/beats/winlogbeat.go rename to agent/collectors/winlogbeat.go index 75ae5404a..d39fbf1e6 100644 --- a/agent/agent/beats/winlogbeat.go +++ b/agent/collectors/winlogbeat.go @@ -1,32 +1,28 @@ -package beats +package collectors import ( "fmt" "path/filepath" - "github.com/threatwinds/logger" "github.com/threatwinds/validations" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/logservice" - "github.com/utmstack/UTMStack/agent/agent/utils" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/logservice" + "github.com/utmstack/UTMStack/agent/utils" ) type Winlogbeat struct{} func (w Winlogbeat) Install() error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("error getting current path: %v", err) - } + path := utils.GetMyPath() winlogPath := filepath.Join(path, "beats", "winlogbeat") - beatConfig := BeatConfig{ + beatConfig := CollectorConfig{ LogsPath: filepath.Join(winlogPath, "logs"), LogFileName: "windowscollector", } - if isInstalled, err := utils.CheckIfServiceIsInstalled(configuration.WinServName); err != nil { - return fmt.Errorf("error checking if %s service is installed: %v", configuration.WinServName, err) + if isInstalled, err := utils.CheckIfServiceIsInstalled(config.WinServName); err != nil { + return fmt.Errorf("error checking if %s service is installed: %v", config.WinServName, err) } else if !isInstalled { err = utils.CreatePathIfNotExist(beatConfig.LogsPath) if err != nil { @@ -43,63 +39,60 @@ func (w Winlogbeat) Install() error { err = utils.Execute("sc", winlogPath, "create", - configuration.WinServName, + config.WinServName, "binPath=", fmt.Sprintf("\"%s\\winlogbeat.exe\" --environment=windows_service -c \"%s\\winlogbeat.yml\" --path.home \"%s\" --path.data \"C:\\ProgramData\\winlogbeat\" --path.logs \"C:\\ProgramData\\winlogbeat\\logs\" -E logging.files.redirect_stderr=true", winlogPath, winlogPath, winlogPath), "DisplayName=", - configuration.WinServName, + config.WinServName, "start=", "auto") if err != nil { - return fmt.Errorf("error installing %s service: %s", configuration.WinServName, err) + return fmt.Errorf("error installing %s service: %s", config.WinServName, err) } - err = utils.Execute("sc", winlogPath, "start", configuration.WinServName) + err = utils.Execute("sc", winlogPath, "start", config.WinServName) if err != nil { - return fmt.Errorf("error starting %s service: %s", configuration.WinServName, err) + return fmt.Errorf("error starting %s service: %s", config.WinServName, err) } } return nil } -func (w Winlogbeat) SendSystemLogs(h *logger.Logger) { +func (w Winlogbeat) SendSystemLogs() { logLinesChan := make(chan []string) - path, err := utils.GetMyPath() - if err != nil { - h.ErrorF("error getting current path: %v", err) - } + path := utils.GetMyPath() winbLogPath := filepath.Join(path, "beats", "winlogbeat", "logs") - go utils.WatchFolder("windowscollector", winbLogPath, logLinesChan, configuration.BatchCapacity, h) + go utils.WatchFolder("windowscollector", winbLogPath, logLinesChan, config.BatchCapacity) for logLine := range logLinesChan { validatedLogs := []string{} for _, log := range logLine { validatedLog, _, err := validations.ValidateString(log, false) if err != nil { - h.ErrorF("error validating log: %s: %v", log, err) + utils.Logger.ErrorF("error validating log: %s: %v", log, err) continue } validatedLogs = append(validatedLogs, validatedLog) } logservice.LogQueue <- logservice.LogPipe{ - Src: string(configuration.LogTypeWindowsAgent), + Src: string(config.DataTypeWindowsAgent), Logs: validatedLogs, } } } func (w Winlogbeat) Uninstall() error { - if isInstalled, err := utils.CheckIfServiceIsInstalled(configuration.WinServName); err != nil { - return fmt.Errorf("error checking if %s is running: %v", configuration.WinServName, err) + if isInstalled, err := utils.CheckIfServiceIsInstalled(config.WinServName); err != nil { + return fmt.Errorf("error checking if %s is running: %v", config.WinServName, err) } else if isInstalled { - err = utils.StopService(configuration.WinServName) + err = utils.StopService(config.WinServName) if err != nil { - return fmt.Errorf("error stopping %s: %v", configuration.WinServName, err) + return fmt.Errorf("error stopping %s: %v", config.WinServName, err) } - err = utils.UninstallService(configuration.WinServName) + err = utils.UninstallService(config.WinServName) if err != nil { - return fmt.Errorf("error uninstalling %s: %v", configuration.WinServName, err) + return fmt.Errorf("error uninstalling %s: %v", config.WinServName, err) } } diff --git a/agent/agent/configuration/config.go b/agent/config/config.go similarity index 68% rename from agent/agent/configuration/config.go rename to agent/config/config.go index 38ed72fbf..8e41ef88f 100644 --- a/agent/agent/configuration/config.go +++ b/agent/config/config.go @@ -1,14 +1,13 @@ -package configuration +package config import ( "fmt" "os" - "path/filepath" "sync" aesCrypt "github.com/AtlasInsideCorp/AtlasInsideAES" "github.com/google/uuid" - "github.com/utmstack/UTMStack/agent/agent/utils" + "github.com/utmstack/UTMStack/agent/utils" ) type InstallationUUID struct { @@ -45,30 +44,24 @@ var ( func GetCurrentConfig() (*Config, error) { var errR error confOnce.Do(func() { - path, err := utils.GetMyPath() - if err != nil { - errR = fmt.Errorf("failed to get current path: %v", err) - return - } - - uuidExists := utils.CheckIfPathExist(filepath.Join(path, UUIDFileName)) + uuidExists := utils.CheckIfPathExist(UUIDFileName) var encryptConfig Config - if err = utils.ReadYAML(filepath.Join(path, "config.yml"), &encryptConfig); err != nil { + if err := utils.ReadYAML(ConfigurationFile, &encryptConfig); err != nil { errR = fmt.Errorf("error reading config file: %v", err) return } - // Get key var key []byte + var err error if uuidExists { - uuid, err := GetUUID() + id, err := GetUUID() if err != nil { errR = fmt.Errorf("failed to get uuid: %v", err) return } - key, err = utils.GenerateKeyByUUID(REPLACE_KEY, uuid) + key, err = utils.GenerateKeyByUUID(REPLACE_KEY, id) if err != nil { errR = fmt.Errorf("error geneating key: %v", err) return @@ -81,7 +74,6 @@ func GetCurrentConfig() (*Config, error) { } } - // Decrypt config agentKey, err := aesCrypt.AESDecrypt(encryptConfig.AgentKey, key) if err != nil { errR = fmt.Errorf("error encoding agent key: %v", err) @@ -107,24 +99,16 @@ func GetCurrentConfig() (*Config, error) { } func SaveConfig(cnf *Config) error { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } - - uuid, err := GenerateNewUUID() + id, err := GenerateNewUUID() if err != nil { return fmt.Errorf("failed to generate uuid: %v", err) } - // Get key - key, err := utils.GenerateKeyByUUID(REPLACE_KEY, uuid) + key, err := utils.GenerateKeyByUUID(REPLACE_KEY, id) if err != nil { return fmt.Errorf("error geneating key: %v", err) } - // Encrypt config agentKey, err := aesCrypt.AESEncrypt(cnf.AgentKey, key) if err != nil { return fmt.Errorf("error encoding agent key: %v", err) @@ -137,8 +121,7 @@ func SaveConfig(cnf *Config) error { SkipCertValidation: cnf.SkipCertValidation, } - // Write config in config.yml - if err := utils.WriteYAML(filepath.Join(path, "config.yml"), encryptConf); err != nil { + if err := utils.WriteYAML(ConfigurationFile, encryptConf); err != nil { return err } return nil @@ -154,12 +137,7 @@ func GenerateNewUUID() (string, error) { UUID: uuid.String(), } - path, err := utils.GetMyPath() - if err != nil { - return "", fmt.Errorf("failed to get current path: %v", err) - } - - if err = utils.WriteYAML(filepath.Join(path, UUIDFileName), InstallationUUID); err != nil { + if err = utils.WriteYAML(UUIDFileName, InstallationUUID); err != nil { return "", fmt.Errorf("error writing uuid file: %v", err) } @@ -169,19 +147,13 @@ func GenerateNewUUID() (string, error) { func GetUUID() (string, error) { var errR error instuuidOnce.Do(func() { - path, err := utils.GetMyPath() - if err != nil { - errR = fmt.Errorf("failed to get current path: %v", err) - return - } - - var uuid = InstallationUUID{} - if err = utils.ReadYAML(filepath.Join(path, UUIDFileName), &uuid); err != nil { + var id = InstallationUUID{} + if err := utils.ReadYAML(UUIDFileName, &id); err != nil { errR = fmt.Errorf("error reading uuid file: %v", err) return } - instuuid = uuid.UUID + instuuid = id.UUID }) if errR != nil { diff --git a/agent/config/const.go b/agent/config/const.go new file mode 100644 index 000000000..51ce80aae --- /dev/null +++ b/agent/config/const.go @@ -0,0 +1,132 @@ +package config + +import ( + "path/filepath" + + "github.com/utmstack/UTMStack/agent/utils" +) + +const REPLACE_KEY string = "" + +type DataType string + +type ProtoPort struct { + UDP string + TCP string +} + +var ( + DependUrl = "https://%s:%s/private/dependencies/agent/%s" + AgentManagerPort = "9000" + LogAuthProxyPort = "50051" + DependenciesPort = "9001" + + ServiceLogFile = filepath.Join(utils.GetMyPath(), "logs", "utmstack_agent.log") + ModulesServName = "UTMStackModulesLogsCollector" + WinServName = "UTMStackWindowsLogsCollector" + CollectorFileName = filepath.Join(utils.GetMyPath(), "log-collector-config.json") + CollectorFileNameOld = filepath.Join(utils.GetMyPath(), "log-collector-configuration.json") + UUIDFileName = filepath.Join(utils.GetMyPath(), "uuid.yml") + ConfigurationFile = filepath.Join(utils.GetMyPath(), "config.yml") + PortRangeMin = "7000" + PortRangeMax = "9000" + RetentionConfigFile = filepath.Join(utils.GetMyPath(), "retention.json") + LogsDBFile = filepath.Join(utils.GetMyPath(), "logs_process", "logs.db") + CertPath = filepath.Join(utils.GetMyPath(), "certs", "utm.crt") + VersionPath = filepath.Join(utils.GetMyPath(), "version.json") + MESSAGE_HEADER = "utm_stack_agent_ds" + BatchCapacity = 100 + + // MaxConnectionTime = 120 * time.Second + // SERV_NAME = "UTMStackAgent" + // SERV_LOG = "utmstack_agent.log" + // ModulesLockName = "utmstack_modules_collector.lock" + // WinLockName = "utmstack_windows_collector.lock" + // RedlineLockName = "utmstack_redline.lock" + // RedlineServName = "UTMStackRedline" + // BatchToSend = 5 + + DataTypeWindowsAgent DataType = "wineventlog" + DataTypeSyslog DataType = "syslog" + DataTypeVmware DataType = "vmware-esxi" + DataTypeLinuxAgent DataType = "linux" + DataTypeEset DataType = "antivirus-esmc-eset" + DataTypeKaspersky DataType = "antivirus-kaspersky" + DataTypeTraefikModule DataType = "traefik" + DataTypeMongodbModule DataType = "mongodb" + DataTypeMysqlModule DataType = "mysql" + DataTypePostgresqlModule DataType = "postgresql" + DataTypeRedisModule DataType = "redis" + DataTypeElasticsearchModule DataType = "elasticsearch" + DataTypeKafkaModule DataType = "kafka" + DataTypeKibanaModule DataType = "kibana" + DataTypeLogstashModule DataType = "logstash" + DataTypeCiscoAsa DataType = "firewall-cisco-asa" + DataTypeCiscoMeraki DataType = "firewall-meraki" + DataTypeFortinet DataType = "firewall-fortigate-traffic" + DataTypePaloalto DataType = "firewall-paloalto" + DataTypeMikrotik DataType = "firewall-mikrotik" + DataTypeCiscoFirepower DataType = "firewall-cisco-firepower" + DataTypeSophosXG DataType = "firewall-sophos-xg" + DataTypeCiscoSwitch DataType = "cisco-switch" + DataTypeSonicwall DataType = "firewall-sonicwall" + DataTypeNatsModule DataType = "nats" + DataTypeDeceptivebytes DataType = "deceptive-bytes" + DataTypeOsqueryModule DataType = "osquery" + DataTypeLinuxAuditdModule DataType = "auditd" + DataTypeHaproxyModule DataType = "haproxy" + DataTypeNginxModule DataType = "nginx" + DataTypeIisModule DataType = "iis" + DataTypeApacheModule DataType = "apache" + DataTypeSentinelOne DataType = "antivirus-sentinel-one" + DataTypeCiscoGeneric DataType = "cisco" + DataTypeMacOs DataType = "macos" + DataTypeGeneric DataType = "generic" + DataTypeNetflow DataType = "netflow" + DataTypeAix DataType = "ibm-aix" + DataTypePfsense DataType = "firewall-pfsense" + DataTypeFortiweb DataType = "firewall-fortiweb" + + ProtoPorts = map[DataType]ProtoPort{ + DataTypeSyslog: {UDP: "7014", TCP: "7014"}, + DataTypeVmware: {UDP: "7002", TCP: "7002"}, + DataTypeEset: {UDP: "7003", TCP: "7003"}, + DataTypeKaspersky: {UDP: "7004", TCP: "7004"}, + DataTypeCiscoGeneric: {UDP: "514", TCP: "1470"}, + DataTypeFortinet: {UDP: "7005", TCP: "7005"}, + DataTypePaloalto: {UDP: "7006", TCP: "7006"}, + DataTypeMikrotik: {UDP: "7007", TCP: "7007"}, + DataTypeSophosXG: {UDP: "7008", TCP: "7008"}, + DataTypeSonicwall: {UDP: "7009", TCP: "7009"}, + DataTypeDeceptivebytes: {UDP: "7010", TCP: "7010"}, + DataTypeSentinelOne: {UDP: "7012", TCP: "7012"}, + DataTypeMacOs: {UDP: "7015", TCP: "7015"}, + DataTypeAix: {UDP: "7016", TCP: "7016"}, + DataTypePfsense: {UDP: "7017", TCP: "7017"}, + DataTypeFortiweb: {UDP: "7018", TCP: "7018"}, + DataTypeNetflow: {UDP: "2055", TCP: ""}, + } + + ProhibitedPortsChange = []DataType{DataTypeCiscoGeneric, DataTypeNetflow} +) + +func GetMessageFormated(host string, msg string) string { + return "[" + MESSAGE_HEADER + "=" + host + "]-" + msg +} + +func ValidateModuleType(typ string) string { + switch DataType(typ) { + case DataTypeSyslog, DataTypeVmware, DataTypeEset, DataTypeKaspersky, DataTypeFortinet, DataTypePaloalto, + DataTypeMikrotik, DataTypeSophosXG, DataTypeSonicwall, DataTypeSentinelOne, DataTypeCiscoGeneric, DataTypeMacOs, + DataTypeDeceptivebytes, DataTypeAix, DataTypePfsense, DataTypeFortiweb: + return "syslog" + case DataTypeNetflow: + return "netflow" + case DataTypeWindowsAgent, DataTypeLinuxAgent, DataTypeTraefikModule, DataTypeMongodbModule, DataTypeMysqlModule, DataTypePostgresqlModule, + DataTypeRedisModule, DataTypeElasticsearchModule, DataTypeKafkaModule, DataTypeKibanaModule, DataTypeLogstashModule, DataTypeNatsModule, + DataTypeOsqueryModule, DataTypeLinuxAuditdModule, DataTypeHaproxyModule, DataTypeNginxModule, DataTypeIisModule, DataTypeApacheModule: + return "beats" + default: + return "nil" + } +} diff --git a/agent/config/linux_amd64.go b/agent/config/linux_amd64.go new file mode 100644 index 000000000..76c777a2b --- /dev/null +++ b/agent/config/linux_amd64.go @@ -0,0 +1,10 @@ +//go:build linux && amd64 +// +build linux,amd64 + +package config + +var ( + UpdaterSelf = "utmstack_updater_self%s" + ServiceFile = "utmstack_agent_service%s" + DependFiles = []string{"utmstack_agent_dependencies_linux.zip"} +) diff --git a/agent/config/linux_arm64.go b/agent/config/linux_arm64.go new file mode 100644 index 000000000..138c70002 --- /dev/null +++ b/agent/config/linux_arm64.go @@ -0,0 +1,10 @@ +//go:build linux && arm64 +// +build linux,arm64 + +package config + +var ( + UpdaterSelf = "utmstack_updater_self_arm64%s" + ServiceFile = "utmstack_agent_service_arm64%s" + DependFiles = []string{"utmstack_agent_dependencies_linux_arm64.zip"} +) diff --git a/agent/config/win_amd64.go b/agent/config/win_amd64.go new file mode 100644 index 000000000..af4490cd0 --- /dev/null +++ b/agent/config/win_amd64.go @@ -0,0 +1,10 @@ +//go:build windows && amd64 +// +build windows,amd64 + +package config + +var ( + UpdaterSelf = "utmstack_updater_self%s.exe" + ServiceFile = "utmstack_agent_service%s.exe" + DependFiles = []string{"utmstack_agent_dependencies_windows.zip"} +) diff --git a/agent/config/win_arm64.go b/agent/config/win_arm64.go new file mode 100644 index 000000000..aa136d400 --- /dev/null +++ b/agent/config/win_arm64.go @@ -0,0 +1,10 @@ +//go:build windows && arm64 +// +build windows,arm64 + +package config + +var ( + UpdaterSelf = "utmstack_updater_self_arm64%s.exe" + ServiceFile = "utmstack_agent_service_arm64%s.exe" + DependFiles = []string{"utmstack_agent_dependencies_windows_arm64.zip"} +) diff --git a/agent/conn/conn.go b/agent/conn/conn.go new file mode 100644 index 000000000..e045ca020 --- /dev/null +++ b/agent/conn/conn.go @@ -0,0 +1,118 @@ +package conn + +import ( + "crypto/tls" + "fmt" + "sync" + "time" + + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/utils" + grpc "google.golang.org/grpc" + "google.golang.org/grpc/connectivity" + "google.golang.org/grpc/credentials" +) + +const ( + maxMessageSize = 1024 * 1024 * 1024 + maxConnectionAttempts = 3 + initialReconnectDelay = 10 * time.Second + maxReconnectDelay = 60 * time.Second +) + +var ( + correlationConn *grpc.ClientConn + correlationConnOnce sync.Once + agentManagerConn *grpc.ClientConn + agentManagerConnOnce sync.Once +) + +func GetAgentManagerConnection(cnf *config.Config) (*grpc.ClientConn, error) { + var err error + agentManagerConnOnce.Do(func() { + agentManagerConn, err = connectToServer(cnf.Server, config.AgentManagerPort, cnf.SkipCertValidation) + if err != nil { + err = fmt.Errorf("error connecting to Agent Manager: %v", err) + } + }) + if err != nil { + return nil, err + } + + state := agentManagerConn.GetState() + if state == connectivity.Shutdown || state == connectivity.TransientFailure { + agentManagerConn.Close() + agentManagerConn, err = connectToServer(cnf.Server, config.AgentManagerPort, cnf.SkipCertValidation) + if err != nil { + return nil, fmt.Errorf("error connecting to Agent Manager: %v", err) + } + } + + return agentManagerConn, nil +} + +func GetCorrelationConnection(cnf *config.Config) (*grpc.ClientConn, error) { + var err error + correlationConnOnce.Do(func() { + correlationConn, err = connectToServer(cnf.Server, config.LogAuthProxyPort, cnf.SkipCertValidation) + if err != nil { + err = fmt.Errorf("error connecting to Correlation: %v", err) + } + }) + if err != nil { + return nil, err + } + + state := correlationConn.GetState() + if state == connectivity.Shutdown || state == connectivity.TransientFailure { + correlationConn.Close() + correlationConn, err = connectToServer(cnf.Server, config.LogAuthProxyPort, cnf.SkipCertValidation) + if err != nil { + return nil, fmt.Errorf("error connecting to Correlation: %v", err) + } + } + + return correlationConn, nil +} + +func connectToServer(addrs, port string, skip bool) (*grpc.ClientConn, error) { + connectionAttemps := 0 + reconnectDelay := initialReconnectDelay + + serverAddress := addrs + ":" + port + var conn *grpc.ClientConn + var err error + + for { + if connectionAttemps >= maxConnectionAttempts { + return nil, fmt.Errorf("failed to connect to Server: %v", err) + } + + dialOptions := []grpc.DialOption{ + grpc.WithDefaultCallOptions(grpc.MaxCallRecvMsgSize(maxMessageSize)), + } + + if !skip { + tlsCredentials, err := utils.LoadGRPCTLSCredentials(config.CertPath) + if err != nil { + return nil, fmt.Errorf("failed to load TLS credentials: %v", err) + } + dialOptions = append(dialOptions, grpc.WithTransportCredentials(tlsCredentials)) + } else { + dialOptions = append(dialOptions, grpc.WithTransportCredentials(credentials.NewTLS(&tls.Config{}))) + } + + conn, err = grpc.NewClient(serverAddress, dialOptions...) + if err != nil { + connectionAttemps++ + utils.Logger.ErrorF("error connecting to Server, trying again in %.0f seconds", reconnectDelay.Seconds()) + time.Sleep(reconnectDelay) + reconnectDelay = utils.IncrementReconnectDelay(reconnectDelay, maxReconnectDelay) + continue + } + + break + } + + return conn, nil +} diff --git a/agent/agent/go.mod b/agent/go.mod similarity index 73% rename from agent/agent/go.mod rename to agent/go.mod index f0e2355d0..e25ed3f7a 100644 --- a/agent/agent/go.mod +++ b/agent/go.mod @@ -1,18 +1,18 @@ -module github.com/utmstack/UTMStack/agent/agent +module github.com/utmstack/UTMStack/agent -go 1.22.4 +go 1.23.0 toolchain go1.23.4 require ( github.com/AtlasInsideCorp/AtlasInsideAES v1.0.0 - github.com/elastic/go-sysinfo v1.11.1 + github.com/elastic/go-sysinfo v1.15.1 github.com/google/uuid v1.6.0 github.com/kardianos/service v1.2.2 github.com/tehmaze/netflow v0.0.0-20240303214733-8c13bb004068 - github.com/threatwinds/logger v1.1.12 - github.com/threatwinds/validations v1.0.5 - google.golang.org/grpc v1.70.0 + github.com/threatwinds/logger v1.2.1 + github.com/threatwinds/validations v1.0.9 + google.golang.org/grpc v1.71.0 google.golang.org/protobuf v1.36.5 gopkg.in/yaml.v2 v2.4.0 ) @@ -30,7 +30,6 @@ require ( github.com/go-playground/universal-translator v0.18.1 // indirect github.com/go-playground/validator/v10 v10.22.0 // indirect github.com/goccy/go-json v0.10.3 // indirect - github.com/joeshaw/multierror v0.0.0-20140124173710-69b34d4ec901 // indirect github.com/json-iterator/go v1.1.12 // indirect github.com/klauspost/cpuid/v2 v2.2.8 // indirect github.com/leodido/go-urn v1.4.0 // indirect @@ -39,15 +38,15 @@ require ( github.com/modern-go/reflect2 v1.0.2 // indirect github.com/pelletier/go-toml/v2 v2.2.2 // indirect github.com/pkg/errors v0.9.1 // indirect - github.com/prometheus/procfs v0.8.0 // indirect + github.com/prometheus/procfs v0.15.1 // indirect github.com/twitchyliquid64/golang-asm v0.15.1 // indirect github.com/ugorji/go/codec v1.2.12 // indirect golang.org/x/arch v0.9.0 // indirect - golang.org/x/crypto v0.31.0 // indirect - golang.org/x/net v0.32.0 // indirect - golang.org/x/sys v0.28.0 // indirect - golang.org/x/text v0.21.0 // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20241202173237-19429a94021a // indirect + golang.org/x/crypto v0.36.0 // indirect + golang.org/x/net v0.37.0 // indirect + golang.org/x/sys v0.31.0 // indirect + golang.org/x/text v0.23.0 // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20250115164207-1a7da9e5054f // indirect gopkg.in/natefinch/lumberjack.v2 v2.2.1 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect howett.net/plist v0.0.0-20181124034731-591f970eefbb // indirect diff --git a/agent/agent/go.sum b/agent/go.sum similarity index 67% rename from agent/agent/go.sum rename to agent/go.sum index 5862389e1..192c8f5ac 100644 --- a/agent/agent/go.sum +++ b/agent/go.sum @@ -1,7 +1,5 @@ github.com/AtlasInsideCorp/AtlasInsideAES v1.0.0 h1:TBiBl9KCa4i4epY0/q9WSC4ugavL6+6JUkOXWDnMM6I= github.com/AtlasInsideCorp/AtlasInsideAES v1.0.0/go.mod h1:cRhQ3TS/VEfu/z+qaciyuDZdtxgaXgaX8+G6Wa5NzBk= -github.com/Microsoft/go-winio v0.6.0 h1:slsWYD/zyx7lCXoZVlvQrj0hPTM1HI4+v1sIda2yDvg= -github.com/Microsoft/go-winio v0.6.0/go.mod h1:cTAf44im0RAYeL23bpB+fzCyDH2MJiz2BO69KH/soAE= github.com/bytedance/sonic v1.12.1 h1:jWl5Qz1fy7X1ioY74WqO0KjAMtAGQs4sYnjiEBiyX24= github.com/bytedance/sonic v1.12.1/go.mod h1:B8Gt/XvtZ3Fqj+iSKMypzymZxw/FVwgIGKzMzT9r/rk= github.com/bytedance/sonic/loader v0.1.1/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= @@ -14,16 +12,8 @@ github.com/cloudwego/iasm v0.2.0/go.mod h1:8rXZaNYT2n95jn+zTI1sDr+IgcD2GVs0nlbbQ github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/docker/distribution v2.8.2+incompatible h1:T3de5rq0dB1j30rp0sA2rER+m322EBzniBPB6ZIzuh8= -github.com/docker/distribution v2.8.2+incompatible/go.mod h1:J2gT2udsDAN96Uj4KfcMRqY0/ypR+oyYUYmja8H+y+w= -github.com/docker/docker v23.0.3+incompatible h1:9GhVsShNWz1hO//9BNg/dpMnZW25KydO4wtVxWAIbho= -github.com/docker/docker v23.0.3+incompatible/go.mod h1:eEKB0N0r5NX/I1kEveEz05bcu8tLC/8azJZsviup8Sk= -github.com/docker/go-connections v0.4.0 h1:El9xVISelRB7BuFusrZozjnkIM5YnzCViNKohAFqRJQ= -github.com/docker/go-connections v0.4.0/go.mod h1:Gbd7IOopHjR8Iph03tsViu4nIes5XhDvyHbTtUxmeec= -github.com/docker/go-units v0.5.0 h1:69rxXcBk27SvSaaxTtLh/8llcHD8vYHT7WSdRZ/jvr4= -github.com/docker/go-units v0.5.0/go.mod h1:fgPhTUdO+D/Jk86RDLlptpiXQzgHJF7gydDDbaIK4Dk= -github.com/elastic/go-sysinfo v1.11.1 h1:g9mwl05njS4r69TisC+vwHWTSKywZFYYUu3so3T/Lao= -github.com/elastic/go-sysinfo v1.11.1/go.mod h1:6KQb31j0QeWBDF88jIdWSxE8cwoOB9tO4Y4osN7Q70E= +github.com/elastic/go-sysinfo v1.15.1 h1:zBmTnFEXxIQ3iwcQuk7MzaUotmKRp3OabbbWM8TdzIQ= +github.com/elastic/go-sysinfo v1.15.1/go.mod h1:jPSuTgXG+dhhh0GKIyI2Cso+w5lPJ5PvVqKlL8LV/Hk= github.com/elastic/go-windows v1.0.0 h1:qLURgZFkkrYyTTkvYpsZIgf83AUsdIHfvlJaqaZ7aSY= github.com/elastic/go-windows v1.0.0/go.mod h1:TsU0Nrp7/y3+VwE82FoZF8gC/XFg/Elz6CcloAxnPgU= github.com/gabriel-vasile/mimetype v1.4.5 h1:J7wGKdGu33ocBOhGy0z653k/lFKLFDPJMG8Gql0kxn4= @@ -46,8 +36,6 @@ github.com/go-playground/validator/v10 v10.22.0 h1:k6HsTZ0sTnROkhS//R0O+55JgM8C4 github.com/go-playground/validator/v10 v10.22.0/go.mod h1:dbuPbCMFw/DrkbEynArYaCwl3amGuJotoKCe95atGMM= github.com/goccy/go-json v0.10.3 h1:KZ5WoDbxAIgm2HNbYckL0se1fHD6rz5j4ywS6ebzDqA= github.com/goccy/go-json v0.10.3/go.mod h1:oq7eo15ShAhp70Anwd5lgX2pLfOS3QCiwU/PULtXL6M= -github.com/gogo/protobuf v1.3.2 h1:Ov1cvc58UF3b5XjBnZv7+opcTcQFZebYjWzi34vdm4Q= -github.com/gogo/protobuf v1.3.2/go.mod h1:P1XiOD3dCwIKUDQYPy72D8LYyHL2YPYrpS2s69NZV8Q= github.com/golang/protobuf v1.5.4 h1:i7eJL8qZTpSEXOPTxNKhASYpMn+8e5Q6AdndVa1dWek= github.com/golang/protobuf v1.5.4/go.mod h1:lnTiLA8Wa4RWRcIUkrtSVa5nRhsEGBg48fD6rSs7xps= github.com/google/go-cmp v0.6.0 h1:ofyhxvXcZhMsU5ulbFiLKl/XBFqE1GSq7atu8tAmTRI= @@ -56,8 +44,6 @@ github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/ github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= github.com/jessevdk/go-flags v1.4.0/go.mod h1:4FA24M0QyGHXBuZZK/XkWh8h0e1EYbRYJSGM75WSRxI= -github.com/joeshaw/multierror v0.0.0-20140124173710-69b34d4ec901 h1:rp+c0RAYOWj8l6qbCUTSiRLG/iKnW3K3/QfPPuSsBt4= -github.com/joeshaw/multierror v0.0.0-20140124173710-69b34d4ec901/go.mod h1:Z86h9688Y0wesXCyonoVr47MasHilkuLMqGhRZ4Hpak= github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= github.com/kardianos/service v1.2.2 h1:ZvePhAHfvo0A7Mftk/tEzqEZ7Q4lgnR8sGz4xu1YX60= @@ -80,10 +66,6 @@ github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= -github.com/opencontainers/go-digest v1.0.0 h1:apOUWs51W5PlhuyGyz9FCeeBIOUDA/6nW8Oi/yOhh5U= -github.com/opencontainers/go-digest v1.0.0/go.mod h1:0JzlMkj0TRzQZfJkVvzbP0HBR3IKzErnv2BNG4W4MAM= -github.com/opencontainers/image-spec v1.0.2 h1:9yCKha/T5XdGtO0q9Q9a6T5NUCsTn/DrBg0D7ufOcFM= -github.com/opencontainers/image-spec v1.0.2/go.mod h1:BtxoFyWECRxE4U/7sNtV5W15zMzWCbyJoFRP3s7yZA0= github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM= github.com/pelletier/go-toml/v2 v2.2.2/go.mod h1:1t835xjRzz80PqgE6HHgN2JOsmgYu/h4qDAS4n929Rs= github.com/pkg/errors v0.8.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= @@ -91,8 +73,8 @@ github.com/pkg/errors v0.9.1 h1:FEBLx1zS214owpjy7qsBeixbURkuhQAwrK5UwLGTwt4= github.com/pkg/errors v0.9.1/go.mod h1:bwawxfHBFNV+L2hUp1rHADufV3IMtnDRdf1r5NINEl0= github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= -github.com/prometheus/procfs v0.8.0 h1:ODq8ZFEaYeCaZOJlZZdJA2AbQR98dSHSM1KW/You5mo= -github.com/prometheus/procfs v0.8.0/go.mod h1:z7EfXMXOkbkqb9IINtpCn86r/to3BnA0uaxHdg830/4= +github.com/prometheus/procfs v0.15.1 h1:YagwOFzUgYfKKHX6Dr+sHT7km/hxC76UB0learggepc= +github.com/prometheus/procfs v0.15.1/go.mod h1:fB45yRUv8NstnjriLhBQLuOUt+WW4BsoGhij/e3PBqk= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw= github.com/stretchr/objx v0.5.0/go.mod h1:Yh+to48EsGEfYuaHDzXPcE3xhTkx73EhmCGUpEOglKo= @@ -107,47 +89,43 @@ github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsT github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= github.com/tehmaze/netflow v0.0.0-20240303214733-8c13bb004068 h1:1B+EAUqxEyPByCfk55tB21DtR7WF7Q2w71g7+uVkvIg= github.com/tehmaze/netflow v0.0.0-20240303214733-8c13bb004068/go.mod h1:QRP5wJOf7gGMGL2fCAfmh/5CMZQspRxT5DqghaPRrjM= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= -github.com/threatwinds/validations v1.0.5 h1:kY/Y1g3urTqTNAL/80wWkxPrCHhcbISGduBuVz99d00= -github.com/threatwinds/validations v1.0.5/go.mod h1:vedgpo8crNfHtCMoTlimBlbsFMalXpoTSuSfQh4gU48= +github.com/threatwinds/logger v1.2.1 h1:uN7efZaHobMX3DRi6GOPtxESPxt5xj0bNflnmgklwII= +github.com/threatwinds/logger v1.2.1/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= +github.com/threatwinds/validations v1.0.9 h1:p+DkqNpZ7g+uCmgv2FPDnkOM4ITrNxgauiTmNbVjo/E= +github.com/threatwinds/validations v1.0.9/go.mod h1:POXU59KPuFTXcKl7qNWoQRNc9LiQnjbYBujjqWgW86A= github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= github.com/ugorji/go/codec v1.2.12/go.mod h1:UNopzCgEMSXjBc6AOMqYvWC1ktqTAfzJZUZgYf6w6lg= -go.opentelemetry.io/otel v1.32.0 h1:WnBN+Xjcteh0zdk01SVqV55d/m62NJLJdIyb4y/WO5U= -go.opentelemetry.io/otel v1.32.0/go.mod h1:00DCVSB0RQcnzlwyTfqtxSm+DRr9hpYrHjNGiBHVQIg= -go.opentelemetry.io/otel/metric v1.32.0 h1:xV2umtmNcThh2/a/aCP+h64Xx5wsj8qqnkYZktzNa0M= -go.opentelemetry.io/otel/metric v1.32.0/go.mod h1:jH7CIbbK6SH2V2wE16W05BHCtIDzauciCRLoc/SyMv8= -go.opentelemetry.io/otel/sdk v1.32.0 h1:RNxepc9vK59A8XsgZQouW8ue8Gkb4jpWtJm9ge5lEG4= -go.opentelemetry.io/otel/sdk v1.32.0/go.mod h1:LqgegDBjKMmb2GC6/PrTnteJG39I8/vJCAP9LlJXEjU= -go.opentelemetry.io/otel/sdk/metric v1.32.0 h1:rZvFnvmvawYb0alrYkjraqJq0Z4ZUJAiyYCU9snn1CU= -go.opentelemetry.io/otel/sdk/metric v1.32.0/go.mod h1:PWeZlq0zt9YkYAp3gjKZ0eicRYvOh1Gd+X99x6GHpCQ= -go.opentelemetry.io/otel/trace v1.32.0 h1:WIC9mYrXf8TmY/EXuULKc8hR17vE+Hjv2cssQDe03fM= -go.opentelemetry.io/otel/trace v1.32.0/go.mod h1:+i4rkvCraA+tG6AzwloGaCtkx53Fa+L+V8e9a7YvhT8= +go.opentelemetry.io/auto/sdk v1.1.0 h1:cH53jehLUN6UFLY71z+NDOiNJqDdPRaXzTel0sJySYA= +go.opentelemetry.io/auto/sdk v1.1.0/go.mod h1:3wSPjt5PWp2RhlCcmmOial7AvC4DQqZb7a7wCow3W8A= +go.opentelemetry.io/otel v1.34.0 h1:zRLXxLCgL1WyKsPVrgbSdMN4c0FMkDAskSTQP+0hdUY= +go.opentelemetry.io/otel v1.34.0/go.mod h1:OWFPOQ+h4G8xpyjgqo4SxJYdDQ/qmRH+wivy7zzx9oI= +go.opentelemetry.io/otel/metric v1.34.0 h1:+eTR3U0MyfWjRDhmFMxe2SsW64QrZ84AOhvqS7Y+PoQ= +go.opentelemetry.io/otel/metric v1.34.0/go.mod h1:CEDrp0fy2D0MvkXE+dPV7cMi8tWZwX3dmaIhwPOaqHE= +go.opentelemetry.io/otel/sdk v1.34.0 h1:95zS4k/2GOy069d321O8jWgYsW3MzVV+KuSPKp7Wr1A= +go.opentelemetry.io/otel/sdk v1.34.0/go.mod h1:0e/pNiaMAqaykJGKbi+tSjWfNNHMTxoC9qANsCzbyxU= +go.opentelemetry.io/otel/sdk/metric v1.34.0 h1:5CeK9ujjbFVL5c1PhLuStg1wxA7vQv7ce1EK0Gyvahk= +go.opentelemetry.io/otel/sdk/metric v1.34.0/go.mod h1:jQ/r8Ze28zRKoNRdkjCZxfs6YvBTG1+YIqyFVFYec5w= +go.opentelemetry.io/otel/trace v1.34.0 h1:+ouXS2V8Rd4hp4580a8q23bg0azF2nI8cqLYnC8mh/k= +go.opentelemetry.io/otel/trace v1.34.0/go.mod h1:Svm7lSjQD7kG7KJ/MUHPVXSDGz2OX4h0M2jHBhmSfRE= golang.org/x/arch v0.9.0 h1:ub9TgUInamJ8mrZIGlBG6/4TqWeMszd4N8lNorbrr6k= golang.org/x/arch v0.9.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= -golang.org/x/crypto v0.31.0 h1:ihbySMvVjLAeSH1IbfcRTkD/iNscyz8rGzjF/E5hV6U= -golang.org/x/crypto v0.31.0/go.mod h1:kDsLvtWBEx7MV9tJOj9bnXsPbxwJQ6csT/x4KIN4Ssk= -golang.org/x/mod v0.17.0 h1:zY54UmvipHiNd+pm+m0x9KhZ9hl1/7QNMyxXbc6ICqA= -golang.org/x/mod v0.17.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c= -golang.org/x/net v0.32.0 h1:ZqPmj8Kzc+Y6e0+skZsuACbx+wzMgo5MQsJh9Qd6aYI= -golang.org/x/net v0.32.0/go.mod h1:CwU0IoeOlnQQWJ6ioyFrfRuomB8GKF6KbYXZVyeXNfs= -golang.org/x/sync v0.10.0 h1:3NQrjDixjgGwUOCaF8w2+VYHv0Ve/vGYSbdkTa98gmQ= -golang.org/x/sync v0.10.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk= +golang.org/x/crypto v0.36.0 h1:AnAEvhDddvBdpY+uR+MyHmuZzzNqXSe/GvuDeob5L34= +golang.org/x/crypto v0.36.0/go.mod h1:Y4J0ReaxCR1IMaabaSMugxJES1EpwhBHhv2bDHklZvc= +golang.org/x/net v0.37.0 h1:1zLorHbz+LYj7MQlSf1+2tPIIgibq2eL5xkrGk6f+2c= +golang.org/x/net v0.37.0/go.mod h1:ivrbrMbzFq5J41QOQh0siUuly180yBYtLp+CKbEaFx8= golang.org/x/sys v0.0.0-20201015000850-e3ed0017c211/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.28.0 h1:Fksou7UEQUWlKvIdsqzJmUmCX3cZuD2+P3XyyzwMhlA= -golang.org/x/sys v0.28.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/text v0.21.0 h1:zyQAAkrwaneQ066sspRyJaG9VNi/YJ1NfzcGB3hZ/qo= -golang.org/x/text v0.21.0/go.mod h1:4IBbMaMmOPCJ8SecivzSH54+73PCFmPWxNTLm+vZkEQ= -golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d h1:vU5i/LfpvrRCpgM/VPfJLg5KjxD3E+hfT1SH+d9zLwg= -golang.org/x/tools v0.21.1-0.20240508182429-e35e4ccd0d2d/go.mod h1:aiJjzUbINMkxbQROHiO6hDPo2LHcIPhhQsa9DLh0yGk= -google.golang.org/genproto/googleapis/rpc v0.0.0-20241202173237-19429a94021a h1:hgh8P4EuoxpsuKMXX/To36nOFD7vixReXgn8lPGnt+o= -google.golang.org/genproto/googleapis/rpc v0.0.0-20241202173237-19429a94021a/go.mod h1:5uTbfoYQed2U9p3KIj2/Zzm02PYhndfdmML0qC3q3FU= -google.golang.org/grpc v1.70.0 h1:pWFv03aZoHzlRKHWicjsZytKAiYCtNS0dHbXnIdq7jQ= -google.golang.org/grpc v1.70.0/go.mod h1:ofIJqVKDXx/JiXrwr2IG4/zwdH9txy3IlF40RmcJSQw= +golang.org/x/sys v0.31.0 h1:ioabZlmFYtWhL+TRYpcnNlLwhyxaM9kWTDEmfnprqik= +golang.org/x/sys v0.31.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k= +golang.org/x/text v0.23.0 h1:D71I7dUrlY+VX0gQShAThNGHFxZ13dGLBHQLVl1mJlY= +golang.org/x/text v0.23.0/go.mod h1:/BLNzu4aZCJ1+kcD0DNRotWKage4q2rGVAg4o22unh4= +google.golang.org/genproto/googleapis/rpc v0.0.0-20250115164207-1a7da9e5054f h1:OxYkA3wjPsZyBylwymxSHa7ViiW1Sml4ToBrncvFehI= +google.golang.org/genproto/googleapis/rpc v0.0.0-20250115164207-1a7da9e5054f/go.mod h1:+2Yz8+CLJbIfL9z73EW45avw8Lmge3xVElCP9zEKi50= +google.golang.org/grpc v1.71.0 h1:kF77BGdPTQ4/JZWMlb9VpJ5pa25aqvVqogsxNHHdeBg= +google.golang.org/grpc v1.71.0/go.mod h1:H0GRtasmQOh9LkFoCPDu3ZrwUtD1YGE+b2vYBYd/8Ec= google.golang.org/protobuf v1.36.5 h1:tPhr+woSbjfYvY6/GPufUoYizxw1cF/yFoxJ2fmpwlM= google.golang.org/protobuf v1.36.5/go.mod h1:9fA7Ob0pmnwhb644+1+CVWFRbNajQ6iRojtC/QF5bRE= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= diff --git a/agent/installer/README.md b/agent/installer/README.md deleted file mode 100644 index eeb85263a..000000000 --- a/agent/installer/README.md +++ /dev/null @@ -1,15 +0,0 @@ -# UTMStack Agent Installer -The UTMStack Agent Installer is a Go application that is part of the UTMStack. It is responsible for various tasks including checking versions, managing configurations, handling dependencies, managing services, and providing utility functions. -This installer is designed to install the services that make up the UTMStack agent. These services include UTMStackAgent, UTMStackRedline, UTMStackUpdater, UTMStackWindowsLogsCollector, and UTMStackModulesLogsCollector. - -### Logging -The UTMStack Agent Installer uses a custom logger, referred to as the "beauty logger". This logger is used to print messages to the console in a more readable and aesthetically pleasing format. It also writes error messages and fatal errors to a log file located at path/logs/utmstack_agent_installer.log. - -### Error Handling -If the UTMStack Agent Installer encounters an error during execution, it will log the error and then terminate the program. For example, if it fails to get the current path, or if the required ports (9000 and 50051) are not open, it will log an error message and then call log.Fatalf to terminate the program. - -### Dependencies -The UTMStack Agent Installer has several dependencies that are managed through the depend package. These dependencies are service binaries that the agent needs to function properly. - -### Version Checking -The UTMStack Agent Installer uses the checkversion package to check if the current version of the agent is up to date. If it is not, the agent will update itself to the latest version. diff --git a/agent/installer/agent/oldversion.go b/agent/installer/agent/oldversion.go deleted file mode 100644 index 8019c1641..000000000 --- a/agent/installer/agent/oldversion.go +++ /dev/null @@ -1,141 +0,0 @@ -package agent - -import ( - "fmt" - "os" - "path/filepath" - "runtime" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/runner/utils" -) - -func CleanOldAgent(h *logger.Logger) { - servName := "utmstack" - if isOldInstalled, err := utils.CheckIfServiceIsInstalled(servName); err != nil { - fmt.Printf("error checking utmstack service: %v", err) - h.ErrorF("error checking utmstack service: %v", err) - } else if isOldInstalled { - fmt.Println("Uninstalling UTMStack Agent old version...") - h.Info("Uninstalling UTMStack Agent old version...") - - // Stopping and uninstalling UTMStack Agent old version - err := utils.StopService(servName) - if err != nil { - h.ErrorF("error stopping %s: %v", servName, err) - } - - err = utils.UninstallService(servName) - if err != nil { - h.ErrorF("error uninstalling %s: %v", servName, err) - } - - err = stopWazuh() - if err != nil { - h.ErrorF("error stopping wazuh: %v", err) - } - - // Stopping and uninstalling beats - switch runtime.GOOS { - case "windows": - err := stopWinlogbeat() - if err != nil { - h.ErrorF("%v", err) - } - pathOld := "C:\\Program Files\\UTMStack\\UTMStackAgent" - err = os.RemoveAll(pathOld) - if err != nil { - h.ErrorF("error deleting old agent folder: %v", err) - } - - case "linux": - err := uninstallFilebeat() - if err != nil { - h.ErrorF("%v", err) - } - pathOld := "/opt/linux-agent" - err = os.RemoveAll(pathOld) - if err != nil { - h.ErrorF("error deleting old agent folder: %v", err) - } - } - } -} - -func stopWazuh() error { - servName := "WazuhSvc" - if isInstalled, err := utils.CheckIfServiceIsInstalled(servName); err != nil { - return fmt.Errorf("error checking UTMStackAgent service: %v", err) - } else if isInstalled { - err := utils.StopService(servName) - if err != nil { - return fmt.Errorf("error stopping %s: %v", servName, err) - } - err = utils.UninstallService(servName) - if err != nil { - return fmt.Errorf("error uninstalling %s: %v", servName, err) - } - } - - return nil -} - -func stopWinlogbeat() error { - isRunning, err := utils.IsProcessRunning("winlogbeat") - if err != nil { - return fmt.Errorf("error checking if winlogbeat is running: %v", err) - } else if isRunning { - err = utils.StopProcess("winlogbeat") - if err != nil { - return fmt.Errorf("error stopping winlogbeat: %v", err) - } - } - - return nil -} - -func uninstallFilebeat() error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("error getting current path: %v", err) - } - - err = utils.Execute("systemctl", path, "stop", "filebeat") - if err != nil { - return fmt.Errorf("%s", err) - } - - family, err := utils.DetectLinuxFamily() - if err != nil { - return err - } - - switch family { - case "debian": - err = utils.Execute("apt-get", path, "remove", "--purge", "-y", "filebeat") - if err != nil { - return fmt.Errorf("%s", err) - } - case "rhel": - err = utils.Execute("systemctl", filepath.Join(path, "beats", "filebeat"), "stop", "filebeat") - if err != nil { - return fmt.Errorf("%s", err) - } - err = utils.Execute("systemctl", filepath.Join(path, "beats", "filebeat"), "disable", "filebeat") - if err != nil { - return fmt.Errorf("%s", err) - } - err = utils.Execute("echo", filepath.Join(path, "beats", "filebeat"), "y", "|", "yum", "remove", "filebeat") - if err != nil { - return fmt.Errorf("%s", err) - } - - } - - err = utils.Execute("rm", path, "-rf", "/etc/filebeat") - if err != nil { - return fmt.Errorf("%s", err) - } - - return nil -} diff --git a/agent/installer/checkversion/check_version.go b/agent/installer/checkversion/check_version.go deleted file mode 100644 index 305b72c29..000000000 --- a/agent/installer/checkversion/check_version.go +++ /dev/null @@ -1,46 +0,0 @@ -package checkversion - -import ( - "fmt" - "path/filepath" - "runtime" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/runner/agent" - "github.com/utmstack/UTMStack/agent/runner/utils" -) - -func CleanOldVersions(h *logger.Logger) error { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } - - // Clean UTMStackAgent v9 version - agent.CleanOldAgent(h) - - var exeName string - switch runtime.GOOS { - case "windows": - exeName = filepath.Join(path, "utmstackagent-windows.exe") - case "linux": - exeName = filepath.Join(path, "utmstackagent-linux") - } - - // Check if UTMStackAgent is installed - if isInstalled, err := utils.CheckIfServiceIsInstalled("UTMStackAgent"); err != nil { - return fmt.Errorf("error checking UTMStackAgent service: %v", err) - } else if isInstalled { - if utils.CheckIfPathExist(filepath.Join(path, "version.json")) { - result, errB := utils.ExecuteWithResult(exeName, path, "uninstall") - if errB { - return fmt.Errorf("%s", result) - } - } else { - return fmt.Errorf("UTMStackAgent is already installed") - } - } - - return nil -} diff --git a/agent/installer/configuration/const.go b/agent/installer/configuration/const.go deleted file mode 100644 index eae21173e..000000000 --- a/agent/installer/configuration/const.go +++ /dev/null @@ -1,36 +0,0 @@ -package configuration - -import ( - "path/filepath" - - "github.com/utmstack/UTMStack/agent/runner/utils" -) - -type ServicesBin struct { - AgentServiceBin string - RedlineServiceBin string - UpdaterServiceBin string -} - -const ( - MASTERVERSIONENDPOINT = "/management/info" - INSTALLER_LOG_FILE = "utmstack_agent_installer.log" - Bucket = "https://cdn.utmstack.com/agent_updates/" - AgentManagerPort = "9000" - LogAuthProxyPort = "50051" -) - -func GetCertPath() string { - path, _ := utils.GetMyPath() - return filepath.Join(path, "certs", "utm.crt") -} - -func GetKeyPath() string { - path, _ := utils.GetMyPath() - return filepath.Join(path, "certs", "utm.key") -} - -func GetCaPath() string { - path, _ := utils.GetMyPath() - return filepath.Join(path, "certs", "ca.crt") -} diff --git a/agent/installer/configuration/env.go b/agent/installer/configuration/env.go deleted file mode 100644 index 54a08c444..000000000 --- a/agent/installer/configuration/env.go +++ /dev/null @@ -1,32 +0,0 @@ -package configuration - -import ( - "os" - "path/filepath" - - "github.com/utmstack/UTMStack/agent/runner/utils" -) - -type Environment struct { - Branch string `yaml:"branch"` -} - -func ReadEnv() (*Environment, error) { - var env Environment - path, err := utils.GetMyPath() - if err != nil { - return nil, err - } - - path = filepath.Join(path, "env.yml") - - if _, err = os.Stat(path); os.IsNotExist(err) { - return &Environment{Branch: "release"}, nil - } else { - err = utils.ReadYAML(path, &env) - if err != nil { - return nil, err - } - } - return &env, nil -} diff --git a/agent/installer/depend/checkVersions.go b/agent/installer/depend/checkVersions.go deleted file mode 100644 index 6036e970e..000000000 --- a/agent/installer/depend/checkVersions.go +++ /dev/null @@ -1,78 +0,0 @@ -package depend - -import ( - "crypto/tls" - "fmt" - "net/http" - "path/filepath" - "strings" - - "github.com/utmstack/UTMStack/agent/runner/configuration" - "github.com/utmstack/UTMStack/agent/runner/utils" -) - -func getMasterVersion(ip string, skip bool) (string, error) { - config := &tls.Config{InsecureSkipVerify: skip} - if !skip { - var err error - config, err = utils.LoadTLSCredentials(configuration.GetCertPath()) - if err != nil { - return "", fmt.Errorf("error loading tls credentials: %v", err) - } - } - resp, status, err := utils.DoReq[InfoResponse]("https://"+ip+configuration.MASTERVERSIONENDPOINT, nil, http.MethodGet, map[string]string{}, config) - if err != nil { - return "", err - } else if status != http.StatusOK { - return "", fmt.Errorf("status code %d: %v", status, resp) - } - return resp.Build.Version, nil -} - -func getCurrentVersion(ip string, env string, skip string) (Version, error) { - currentVersion := Version{} - - // Get master version - skipB := skip == "yes" - mastVers, err := getMasterVersion(ip, skipB) - if err != nil { - return currentVersion, fmt.Errorf("error getting master version: %v", err) - } - - path, err := utils.GetMyPath() - if err != nil { - return currentVersion, fmt.Errorf("failed to get current path: %v", err) - } - - err = utils.DownloadFile(configuration.Bucket+env+"/versions.json?time="+utils.GetCurrentTime(), filepath.Join(path, "versions.json")) - if err != nil { - return currentVersion, fmt.Errorf("error downloading versions.json: %v", err) - } - - // Save data from versions.json - var dataVersions DataVersions - err = utils.ReadJson(filepath.Join(path, "versions.json"), &dataVersions) - if err != nil { - return currentVersion, fmt.Errorf("error reading versions.json: %v", err) - } - - versionExist := false - for _, vers := range dataVersions.Versions { - versParts := strings.Split(vers.MasterVersion, ".") - masterParts := strings.Split(mastVers, ".") - - if versParts[0] == masterParts[0] && versParts[1] == masterParts[1] { - versionExist = true - currentVersion = vers - } - } - - if versionExist { - err = utils.WriteJSON(filepath.Join(path, "versions.json"), ¤tVersion) - if err != nil { - return currentVersion, fmt.Errorf("error writing versions.json: %v", err) - } - return currentVersion, nil - } - return currentVersion, fmt.Errorf("error: master version not exist in versions.json") -} diff --git a/agent/installer/depend/dependencies.go b/agent/installer/depend/dependencies.go deleted file mode 100644 index fe6900aaa..000000000 --- a/agent/installer/depend/dependencies.go +++ /dev/null @@ -1,82 +0,0 @@ -package depend - -import ( - "fmt" - "log" - "os" - "path/filepath" - "runtime" - - "github.com/utmstack/UTMStack/agent/runner/configuration" - "github.com/utmstack/UTMStack/agent/runner/utils" -) - -func DownloadDependencies(servBins ServicesBin, ip string, skip string) error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } - - // Select environment - env, err := configuration.ReadEnv() - if err != nil { - return fmt.Errorf("error reading environment configuration: %v", err) - } - - currentVersion, err := getCurrentVersion(ip, env.Branch, skip) - if err != nil { - return fmt.Errorf("error getting current version: %v", err) - } - - urlFiles := map[string]string{ - "dependencies.zip": configuration.Bucket + env.Branch + "/agent_service/v" + currentVersion.AgentVersion + "/" + runtime.GOOS + "_dependencies.zip?time=" + utils.GetCurrentTime(), - servBins.AgentServiceBin: configuration.Bucket + env.Branch + "/agent_service/v" + currentVersion.AgentVersion + "/" + servBins.AgentServiceBin + "?time=" + utils.GetCurrentTime(), - servBins.UpdaterServiceBin: configuration.Bucket + env.Branch + "/updater_service/v" + currentVersion.UpdaterVersion + "/" + servBins.UpdaterServiceBin + "?time=" + utils.GetCurrentTime(), - servBins.RedlineServiceBin: configuration.Bucket + env.Branch + "/redline_service/v" + currentVersion.RedlineVersion + "/" + servBins.RedlineServiceBin + "?time=" + utils.GetCurrentTime(), - } - - for filename, url := range urlFiles { - err = utils.DownloadFile(url, filepath.Join(path, filename)) - if err != nil { - return fmt.Errorf("error downloading dependencies and binaries: %v", err) - } - if runtime.GOOS == "linux" { - if err = utils.Execute("chmod", path, "-R", "777", filename); err != nil { - return fmt.Errorf("error executing chmod: %v", err) - } - } - } - - err = utils.Unzip(filepath.Join(path, "dependencies.zip"), filepath.Join(path)) - if err != nil { - return fmt.Errorf("error unzipping dependencies.zip: %v", err) - } - - if runtime.GOOS == "linux" { - if err = utils.Execute("chmod", path, "-R", "777", "utmstack_updater_self"); err != nil { - return fmt.Errorf("error executing chmod: %v", err) - } - } - - err = os.Remove(filepath.Join(path, "dependencies.zip")) - if err != nil { - log.Printf("error deleting dependencies.zip file: %v\n", err) - } - - return nil -} - -func GetServicesBins() ServicesBin { - servBins := ServicesBin{} - switch runtime.GOOS { - case "windows": - servBins.AgentServiceBin = "utmstack_agent_service.exe" - servBins.UpdaterServiceBin = "utmstack_updater_service.exe" - servBins.RedlineServiceBin = "utmstack_redline_service.exe" - case "linux": - servBins.AgentServiceBin = "utmstack_agent_service" - servBins.UpdaterServiceBin = "utmstack_updater_service" - servBins.RedlineServiceBin = "utmstack_redline_service" - } - return servBins -} diff --git a/agent/installer/depend/schema.go b/agent/installer/depend/schema.go deleted file mode 100644 index 70b2e5605..000000000 --- a/agent/installer/depend/schema.go +++ /dev/null @@ -1,35 +0,0 @@ -package depend - -import "encoding/json" - -type InfoResponse struct { - Display string `json:"display-ribbon-on-profiles"` - Git json.RawMessage `json:"git"` - Build Build `json:"build"` - Profiles []string `json:"activeProfiles"` -} - -type Build struct { - Artifact string `json:"artifact"` - Name string `json:"name"` - Time string `json:"time"` - Version string `json:"version"` - Group string `json:"group"` -} - -type DataVersions struct { - Versions []Version `json:"versions"` -} - -type Version struct { - MasterVersion string `json:"master_version"` - AgentVersion string `json:"agent_version"` - UpdaterVersion string `json:"updater_version"` - RedlineVersion string `json:"redline_version"` -} - -type ServicesBin struct { - AgentServiceBin string - RedlineServiceBin string - UpdaterServiceBin string -} diff --git a/agent/installer/go.mod b/agent/installer/go.mod deleted file mode 100644 index d1409fc66..000000000 --- a/agent/installer/go.mod +++ /dev/null @@ -1,43 +0,0 @@ -module github.com/utmstack/UTMStack/agent/runner - -go 1.22.4 - -toolchain go1.23.4 - -require ( - github.com/logrusorgru/aurora v2.0.3+incompatible - github.com/threatwinds/logger v1.1.12 - gopkg.in/yaml.v2 v2.4.0 -) - -require ( - github.com/bytedance/sonic v1.12.1 // indirect - github.com/bytedance/sonic/loader v0.2.0 // indirect - github.com/cloudwego/base64x v0.1.4 // indirect - github.com/cloudwego/iasm v0.2.0 // indirect - github.com/gabriel-vasile/mimetype v1.4.5 // indirect - github.com/gin-contrib/sse v0.1.0 // indirect - github.com/gin-gonic/gin v1.10.0 // indirect - github.com/go-playground/locales v0.14.1 // indirect - github.com/go-playground/universal-translator v0.18.1 // indirect - github.com/go-playground/validator/v10 v10.22.0 // indirect - github.com/goccy/go-json v0.10.3 // indirect - github.com/google/uuid v1.6.0 // indirect - github.com/json-iterator/go v1.1.12 // indirect - github.com/klauspost/cpuid/v2 v2.2.8 // indirect - github.com/leodido/go-urn v1.4.0 // indirect - github.com/mattn/go-isatty v0.0.20 // indirect - github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect - github.com/modern-go/reflect2 v1.0.2 // indirect - github.com/pelletier/go-toml/v2 v2.2.2 // indirect - github.com/twitchyliquid64/golang-asm v0.15.1 // indirect - github.com/ugorji/go/codec v1.2.12 // indirect - golang.org/x/arch v0.9.0 // indirect - golang.org/x/crypto v0.26.0 // indirect - golang.org/x/net v0.28.0 // indirect - golang.org/x/sys v0.24.0 // indirect - golang.org/x/text v0.17.0 // indirect - google.golang.org/protobuf v1.34.2 // indirect - gopkg.in/natefinch/lumberjack.v2 v2.2.1 // indirect - gopkg.in/yaml.v3 v3.0.1 // indirect -) diff --git a/agent/installer/go.sum b/agent/installer/go.sum deleted file mode 100644 index bd1e6438a..000000000 --- a/agent/installer/go.sum +++ /dev/null @@ -1,98 +0,0 @@ -github.com/bytedance/sonic v1.12.1 h1:jWl5Qz1fy7X1ioY74WqO0KjAMtAGQs4sYnjiEBiyX24= -github.com/bytedance/sonic v1.12.1/go.mod h1:B8Gt/XvtZ3Fqj+iSKMypzymZxw/FVwgIGKzMzT9r/rk= -github.com/bytedance/sonic/loader v0.1.1/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= -github.com/bytedance/sonic/loader v0.2.0 h1:zNprn+lsIP06C/IqCHs3gPQIvnvpKbbxyXQP1iU4kWM= -github.com/bytedance/sonic/loader v0.2.0/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= -github.com/cloudwego/base64x v0.1.4 h1:jwCgWpFanWmN8xoIUHa2rtzmkd5J2plF/dnLS6Xd/0Y= -github.com/cloudwego/base64x v0.1.4/go.mod h1:0zlkT4Wn5C6NdauXdJRhSKRlJvmclQ1hhJgA0rcu/8w= -github.com/cloudwego/iasm v0.2.0 h1:1KNIy1I1H9hNNFEEH3DVnI4UujN+1zjpuk6gwHLTssg= -github.com/cloudwego/iasm v0.2.0/go.mod h1:8rXZaNYT2n95jn+zTI1sDr+IgcD2GVs0nlbbQPiEFhY= -github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= -github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/gabriel-vasile/mimetype v1.4.5 h1:J7wGKdGu33ocBOhGy0z653k/lFKLFDPJMG8Gql0kxn4= -github.com/gabriel-vasile/mimetype v1.4.5/go.mod h1:ibHel+/kbxn9x2407k1izTA1S81ku1z/DlgOW2QE0M4= -github.com/gin-contrib/sse v0.1.0 h1:Y/yl/+YNO8GZSjAhjMsSuLt29uWRFHdHYUb5lYOV9qE= -github.com/gin-contrib/sse v0.1.0/go.mod h1:RHrZQHXnP2xjPF+u1gW/2HnVO7nvIa9PG3Gm+fLHvGI= -github.com/gin-gonic/gin v1.10.0 h1:nTuyha1TYqgedzytsKYqna+DfLos46nTv2ygFy86HFU= -github.com/gin-gonic/gin v1.10.0/go.mod h1:4PMNQiOhvDRa013RKVbsiNwoyezlm2rm0uX/T7kzp5Y= -github.com/go-playground/assert/v2 v2.2.0 h1:JvknZsQTYeFEAhQwI4qEt9cyV5ONwRHC+lYKSsYSR8s= -github.com/go-playground/assert/v2 v2.2.0/go.mod h1:VDjEfimB/XKnb+ZQfWdccd7VUvScMdVu0Titje2rxJ4= -github.com/go-playground/locales v0.14.1 h1:EWaQ/wswjilfKLTECiXz7Rh+3BjFhfDFKv/oXslEjJA= -github.com/go-playground/locales v0.14.1/go.mod h1:hxrqLVvrK65+Rwrd5Fc6F2O76J/NuW9t0sjnWqG1slY= -github.com/go-playground/universal-translator v0.18.1 h1:Bcnm0ZwsGyWbCzImXv+pAJnYK9S473LQFuzCbDbfSFY= -github.com/go-playground/universal-translator v0.18.1/go.mod h1:xekY+UJKNuX9WP91TpwSH2VMlDf28Uj24BCp08ZFTUY= -github.com/go-playground/validator/v10 v10.22.0 h1:k6HsTZ0sTnROkhS//R0O+55JgM8C4Bx7ia+JlgcnOao= -github.com/go-playground/validator/v10 v10.22.0/go.mod h1:dbuPbCMFw/DrkbEynArYaCwl3amGuJotoKCe95atGMM= -github.com/goccy/go-json v0.10.3 h1:KZ5WoDbxAIgm2HNbYckL0se1fHD6rz5j4ywS6ebzDqA= -github.com/goccy/go-json v0.10.3/go.mod h1:oq7eo15ShAhp70Anwd5lgX2pLfOS3QCiwU/PULtXL6M= -github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU= -github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= -github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= -github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= -github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= -github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= -github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= -github.com/klauspost/cpuid/v2 v2.2.8 h1:+StwCXwm9PdpiEkPyzBXIy+M9KUb4ODm0Zarf1kS5BM= -github.com/klauspost/cpuid/v2 v2.2.8/go.mod h1:Lcz8mBdAVJIBVzewtcLocK12l3Y+JytZYpaMropDUws= -github.com/knz/go-libedit v1.10.1/go.mod h1:MZTVkCWyz0oBc7JOWP3wNAzd002ZbM/5hgShxwh4x8M= -github.com/leodido/go-urn v1.4.0 h1:WT9HwE9SGECu3lg4d/dIA+jxlljEa1/ffXKmRjqdmIQ= -github.com/leodido/go-urn v1.4.0/go.mod h1:bvxc+MVxLKB4z00jd1z+Dvzr47oO32F/QSNjSBOlFxI= -github.com/logrusorgru/aurora v2.0.3+incompatible h1:tOpm7WcpBTn4fjmVfgpQq0EfczGlG91VSDkswnjF5A8= -github.com/logrusorgru/aurora v2.0.3+incompatible/go.mod h1:7rIyQOR62GCctdiQpZ/zOJlFyk6y+94wXzv6RNZgaR4= -github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY= -github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y= -github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= -github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= -github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM= -github.com/pelletier/go-toml/v2 v2.2.2/go.mod h1:1t835xjRzz80PqgE6HHgN2JOsmgYu/h4qDAS4n929Rs= -github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= -github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= -github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= -github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw= -github.com/stretchr/objx v0.5.0/go.mod h1:Yh+to48EsGEfYuaHDzXPcE3xhTkx73EhmCGUpEOglKo= -github.com/stretchr/objx v0.5.2/go.mod h1:FRsXN1f5AsAjCGJKqEizvkpNtU+EGNCLh3NxZ/8L+MA= -github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= -github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU= -github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o6fzry7u4= -github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= -github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= -github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= -github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= -github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= -github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= -github.com/ugorji/go/codec v1.2.12/go.mod h1:UNopzCgEMSXjBc6AOMqYvWC1ktqTAfzJZUZgYf6w6lg= -golang.org/x/arch v0.9.0 h1:ub9TgUInamJ8mrZIGlBG6/4TqWeMszd4N8lNorbrr6k= -golang.org/x/arch v0.9.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= -golang.org/x/crypto v0.26.0 h1:RrRspgV4mU+YwB4FYnuBoKsUapNIL5cohGAmSH3azsw= -golang.org/x/crypto v0.26.0/go.mod h1:GY7jblb9wI+FOo5y8/S2oY4zWP07AkOJ4+jxCqdqn54= -golang.org/x/net v0.28.0 h1:a9JDOJc5GMUJ0+UDqmLT86WiEy7iWyIhz8gz8E4e5hE= -golang.org/x/net v0.28.0/go.mod h1:yqtgsTWOOnlGLG9GFRrK3++bGOUEkNBoHZc8MEDWPNg= -golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.24.0 h1:Twjiwq9dn6R1fQcyiK+wQyHWfaz/BJB+YIpzU/Cv3Xg= -golang.org/x/sys v0.24.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/text v0.17.0 h1:XtiM5bkSOt+ewxlOE/aE/AKEHibwj/6gvWMl9Rsh0Qc= -golang.org/x/text v0.17.0/go.mod h1:BuEKDfySbSR4drPmRPG/7iBdf8hvFMuRexcpahXilzY= -golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= -golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= -google.golang.org/protobuf v1.34.2 h1:6xV6lTsCfpGD21XK49h7MhtcApnLqkfYgPcdHftf6hg= -google.golang.org/protobuf v1.34.2/go.mod h1:qYOHts0dSfpeUzUFpOMr/WGzszTmLH+DiWniOlNbLDw= -gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= -gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/natefinch/lumberjack.v2 v2.2.1 h1:bBRl1b0OH9s/DuPhuXpNl+VtCaJXFZ5/uEFST95x9zc= -gopkg.in/natefinch/lumberjack.v2 v2.2.1/go.mod h1:YD8tP3GAjkrDg1eZH7EGmyESg/lsYskCTPBJVb9jqSc= -gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= -gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= -gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= -gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -nullprogram.com/x/optparse v1.0.0/go.mod h1:KdyPE+Igbe0jQUrVfMqDMeJQIJZEuyV7pjYmp6pbG50= diff --git a/agent/installer/main.go b/agent/installer/main.go deleted file mode 100644 index 65dbe9869..000000000 --- a/agent/installer/main.go +++ /dev/null @@ -1,120 +0,0 @@ -package main - -import ( - "log" - "os" - "path/filepath" - "strings" - "time" - - "github.com/utmstack/UTMStack/agent/runner/checkversion" - "github.com/utmstack/UTMStack/agent/runner/configuration" - "github.com/utmstack/UTMStack/agent/runner/depend" - "github.com/utmstack/UTMStack/agent/runner/services" - "github.com/utmstack/UTMStack/agent/runner/utils" -) - -func main() { - beautyLogger := utils.GetBeautyLogger() - beautyLogger.PrintBanner() - - path, err := utils.GetMyPath() - if err != nil { - beautyLogger.WriteError("failed to get current path", err) - log.Fatalf("Failed to get current path: %v", err) - } - - servBins := depend.GetServicesBins() - - var h = utils.CreateLogger(filepath.Join(path, "logs", configuration.INSTALLER_LOG_FILE)) - - if len(os.Args) > 1 { - mode := os.Args[1] - switch mode { - case "install": - ip, utmKey, skip := os.Args[2], os.Args[3], os.Args[4] - - if strings.Count(utmKey, "*") == len(utmKey) { - beautyLogger.WriteError("The connection key provided is incorrect. Please make sure you use the 'copy' icon from the integrations section to get the value of the masked key value.", nil) - h.Fatal("The connection key provided is incorrect. Please make sure you use the 'copy' icon from the integrations section to get the value of the masked key value.") - } - - beautyLogger.WriteSimpleMessage("Installing UTMStack Agent...") - if !utils.IsPortOpen(ip, configuration.AgentManagerPort) || !utils.IsPortOpen(ip, configuration.LogAuthProxyPort) { - beautyLogger.WriteError("one or more of the requiered ports are closed. Please open ports 9000 and 50051.", nil) - h.Fatal("Error installing the UTMStack Agent: one or more of the requiered ports are closed. Please open ports 9000 and 50051.") - } - - err := utils.CreatePathIfNotExist(filepath.Join(path, "locks")) - if err != nil { - beautyLogger.WriteError("error creating locks path", err) - h.Fatal("error creating locks path: %v", err) - } - - err = utils.SetLock(filepath.Join(path, "locks", "setup.lock")) - if err != nil { - beautyLogger.WriteError("error setting setup.lock", err) - h.Fatal("error setting setup.lock: %v", err) - } - - err = checkversion.CleanOldVersions(h) - if err != nil { - beautyLogger.WriteError("error cleaning old versions", err) - h.Fatal("error cleaning old versions: %v", err) - } - - beautyLogger.WriteSimpleMessage("Downloading UTMStack dependencies...") - err = depend.DownloadDependencies(servBins, ip, skip) - if err != nil { - beautyLogger.WriteError("error downloading dependencies", err) - h.Fatal("error downloading dependencies: %v", err) - } - beautyLogger.WriteSuccessfull("UTMStack dependencies downloaded correctly.") - - beautyLogger.WriteSimpleMessage("Installing services...") - err = services.ConfigureServices(servBins, ip, utmKey, skip, "install") - if err != nil { - beautyLogger.WriteError("error installing UTMStack services", err) - h.Fatal("error installing UTMStack services: %v", err) - } - - err = utils.RemoveLock(filepath.Join(path, "locks", "setup.lock")) - if err != nil { - beautyLogger.WriteError("error removing setup.lock", err) - h.Fatal("error removing setup.lock: %v", err) - } - - beautyLogger.WriteSuccessfull("Services installed correctly") - beautyLogger.WriteSuccessfull("UTMStack Agent installed correctly.") - - time.Sleep(5 * time.Second) - os.Exit(0) - - case "uninstall": - beautyLogger.WriteSimpleMessage("Uninstalling UTMStack Agent...") - - if isInstalled, err := utils.CheckIfServiceIsInstalled("UTMStackAgent"); err != nil { - beautyLogger.WriteError("error checking UTMStackAgent service", err) - h.Fatal("error checking UTMStackAgent service: %v", err) - } else if isInstalled { - beautyLogger.WriteSimpleMessage("Uninstalling UTMStack services...") - err = services.ConfigureServices(servBins, "", "", "", "uninstall") - if err != nil { - beautyLogger.WriteError("error uninstalling UTMStack services", err) - h.Fatal("error uninstalling UTMStack services: %v", err) - } - - beautyLogger.WriteSuccessfull("UTMStack services uninstalled correctly.") - time.Sleep(5 * time.Second) - os.Exit(0) - - } else { - beautyLogger.WriteError("UTMStackAgent not installed", nil) - h.Fatal("UTMStackAgent not installed") - } - - default: - beautyLogger.WriteError("unknown option", nil) - } - } -} diff --git a/agent/installer/services/configure.go b/agent/installer/services/configure.go deleted file mode 100644 index ad5a3cf60..000000000 --- a/agent/installer/services/configure.go +++ /dev/null @@ -1,48 +0,0 @@ -package services - -import ( - "fmt" - "strings" - - "github.com/utmstack/UTMStack/agent/runner/depend" - "github.com/utmstack/UTMStack/agent/runner/utils" -) - -func ConfigureServices(bins depend.ServicesBin, ip, utmKey, skip, config string) error { - err := execBin(bins.AgentServiceBin, config, ip, utmKey, skip) - if err != nil { - if strings.Contains(err.Error(), "exit status 1") { - return fmt.Errorf("error %sing UTMStackAgent service: Check the file /logs/utmstack_agent.log for more details", config) - } - return fmt.Errorf("error %sing UTMStackAgent service: %v", config, err) - } - - if config == "install" { - err = execBin(bins.RedlineServiceBin, config) - if err != nil { - if strings.Contains(err.Error(), "exit status 1") { - return fmt.Errorf("error %sing UTMStackRedline service: Check the file /logs/utmstack_redline.log for more details", config) - } - return fmt.Errorf("error %sing UTMStackRedline service: %v", config, err) - } - - err = execBin(bins.UpdaterServiceBin, config) - if err != nil { - if strings.Contains(err.Error(), "exit status 1") { - return fmt.Errorf("error %sing UTMStackUpdater service: Check the file /logs/utmstack_updater.log for more details", config) - } - return fmt.Errorf("error %sing UTMStackUpdater service: %v", config, err) - } - } else if config == "uninstall" { - err = utils.UninstallService("UTMStackRedline") - if err != nil { - return fmt.Errorf("error %sing UTMStackRedline service: %v", config, err) - } - err = utils.UninstallService("UTMStackUpdater") - if err != nil { - return fmt.Errorf("error %sing UTMStackUpdater service: %v", config, err) - } - } - - return err -} diff --git a/agent/installer/services/execBin.go b/agent/installer/services/execBin.go deleted file mode 100644 index d59b264ec..000000000 --- a/agent/installer/services/execBin.go +++ /dev/null @@ -1,31 +0,0 @@ -package services - -import ( - "fmt" - "os" - "path/filepath" - "runtime" - - "github.com/utmstack/UTMStack/agent/runner/utils" -) - -func execBin(binName string, arg ...string) error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } - - if runtime.GOOS == "linux" { - err = os.Chmod(filepath.Join(path, binName), 0755) - if err != nil { - return err - } - } - - result, errB := utils.ExecuteWithResult(filepath.Join(path, binName), path, arg...) - if errB { - return fmt.Errorf("%s", result) - } - - return nil -} diff --git a/agent/installer/utils/beauty.go b/agent/installer/utils/beauty.go deleted file mode 100644 index 46757c4dc..000000000 --- a/agent/installer/utils/beauty.go +++ /dev/null @@ -1,54 +0,0 @@ -package utils - -import ( - "fmt" - "sync" - - "github.com/logrusorgru/aurora" -) - -var ( - beautyLogger *BeautyLogger - beautyLoggerOnce sync.Once -) - -type BeautyLogger struct { -} - -func GetBeautyLogger() *BeautyLogger { - beautyLoggerOnce.Do(func() { - beautyLogger = &BeautyLogger{} - }) - return beautyLogger -} - -func (b *BeautyLogger) WriteError(msg string, err error) { - if err == nil { - fmt.Printf("%s: %s: %s\n", "UTMStack", aurora.Red("error").String(), msg) - } else { - fmt.Printf("%s: %s: %s: %v\n", "UTMStack", aurora.Red("error").String(), msg, err) - } -} - -func (b *BeautyLogger) WriteSuccessfull(msg string) { - fmt.Printf("%s: %s: %s\n", "UTMStack", aurora.Green("success").String(), msg) -} - -func (b *BeautyLogger) WriteSimpleMessage(msg string) { - fmt.Println(msg) -} - -func (b *BeautyLogger) PrintBanner() { - banner := "\n" + - "..........................................................................\n" + - " _ _ _ _____ _ _ \n" + - " | | | | | | / ____| | | | | \n" + - " | | | | | |_ _ __ ___ | (___ | |_ __ _ ___ | | __ \n" + - " | | | | | __| | '_ ` _ \\ \\___ \\ | __| / _` | / __| | |/ / \n" + - " | |__| | | |_ | | | | | | ____) | | |_ | (_| | | (__ | < \n" + - " \\____/ \\__| |_| |_| |_| |_____/ \\__| \\__,_| \\___| |_|\\_\\ \n" + - "..........................................................................\n" + - "\n" - - fmt.Println(banner) -} diff --git a/agent/installer/utils/cmd.go b/agent/installer/utils/cmd.go deleted file mode 100644 index b1881855f..000000000 --- a/agent/installer/utils/cmd.go +++ /dev/null @@ -1,47 +0,0 @@ -package utils - -import ( - "errors" - "os/exec" - "unicode/utf8" -) - -func CleanString(s string) string { - v := make([]rune, 0, len(s)) - for i, r := range s { - if r == utf8.RuneError { - _, size := utf8.DecodeRuneInString(s[i:]) - if size == 1 { - v = append(v, '?') - continue - } - } - v = append(v, r) - } - return string(v) -} - -func ExecuteWithResult(c string, dir string, arg ...string) (string, bool) { - cmd := exec.Command(c, arg...) - - cmd.Dir = dir - if errors.Is(cmd.Err, exec.ErrDot) { - cmd.Err = nil - } - - out, err := cmd.Output() - if err != nil { - return string(out[:]) + err.Error(), true - } - - validUtf8Out := CleanString(string(out[:])) - - return validUtf8Out, false -} - -func Execute(c string, dir string, arg ...string) error { - cmd := exec.Command(c, arg...) - cmd.Dir = dir - - return cmd.Run() -} diff --git a/agent/installer/utils/delay.go b/agent/installer/utils/delay.go deleted file mode 100644 index e3000ea71..000000000 --- a/agent/installer/utils/delay.go +++ /dev/null @@ -1,11 +0,0 @@ -package utils - -import "time" - -func IncrementReconnectDelay(delay time.Duration, maxReconnectDelay time.Duration) time.Duration { - delay *= 2 - if delay > maxReconnectDelay { - delay = maxReconnectDelay - } - return delay -} diff --git a/agent/installer/utils/download.go b/agent/installer/utils/download.go deleted file mode 100644 index a0d578eb0..000000000 --- a/agent/installer/utils/download.go +++ /dev/null @@ -1,51 +0,0 @@ -package utils - -import ( - "fmt" - "io" - "net/http" - "os" - "time" -) - -const ( - maxConnectionAttempts = 3 - initialReconnectDelay = 10 * time.Second - maxReconnectDelay = 60 * time.Second -) - -// DownloadFile downloads a file from a URL and saves it to disk. Returns an error on failure. -func DownloadFile(url string, fileName string) error { - connectionAttemps := 0 - reconnectDelay := initialReconnectDelay - - var resp *http.Response - var err error - - for { - if connectionAttemps >= maxConnectionAttempts { - return fmt.Errorf("error downloading file after %d attemps: %v", maxConnectionAttempts, err) - } - resp, err = http.Get(url) - if err != nil || resp.StatusCode != http.StatusOK { - if resp != nil { - resp.Body.Close() - } - connectionAttemps++ - time.Sleep(reconnectDelay) - reconnectDelay = IncrementReconnectDelay(reconnectDelay, maxReconnectDelay) - continue - } - break - } - defer resp.Body.Close() - - out, err := os.Create(fileName) - if err != nil { - return err - } - defer out.Close() - - _, err = io.Copy(out, resp.Body) - return err -} diff --git a/agent/installer/utils/files.go b/agent/installer/utils/files.go deleted file mode 100644 index 70597446f..000000000 --- a/agent/installer/utils/files.go +++ /dev/null @@ -1,96 +0,0 @@ -package utils - -import ( - "encoding/json" - "fmt" - "os" - "path/filepath" - - "gopkg.in/yaml.v2" -) - -// GetMyPath returns the directory path where the currently running executable is located. -// Returns a string representing the directory path, and an error if any error occurs during the process. -func GetMyPath() (string, error) { - ex, err := os.Executable() - if err != nil { - return "", err - } - exPath := filepath.Dir(ex) - return exPath, nil -} - -// ReadJson reads the json data from the specified file URL and unmarshal it into the provided result interface{}. -// Returns an error if any error occurs during the process. -func ReadJson(fileName string, data interface{}) error { - content, err := os.ReadFile(fileName) - if err != nil { - return err - } - err = json.Unmarshal(content, data) - if err != nil { - return err - } - return nil -} - -// ReadYAML reads the YAML data from the specified file URL and deserializes it into the provided result interface{}. -// Returns an error if any error occurs during the process. -func ReadYAML(path string, result interface{}) error { - file, err := os.Open(path) - if err != nil { - return err - } - defer file.Close() - d := yaml.NewDecoder(file) - if err := d.Decode(result); err != nil { - return err - } - return nil -} - -func CheckIfPathExist(path string) bool { - if _, err := os.Stat(path); os.IsNotExist(err) { - return false - } - return true -} - -func writeToFile(fileName string, body string) error { - file, err := os.OpenFile(fileName, os.O_CREATE|os.O_RDWR|os.O_TRUNC, os.ModePerm) - - if err != nil { - return err - } - - defer file.Close() - - _, err = file.WriteString(body) - return err -} - -func WriteJSON(path string, data interface{}) error { - jsonData, err := json.MarshalIndent(data, "", " ") - if err != nil { - return err - } - - err = writeToFile(path, string(jsonData[:])) - if err != nil { - return err - } - - return nil -} - -// CreatePathIfNotExist creates a specific path if not exist -func CreatePathIfNotExist(path string) error { - if _, err := os.Stat(path); os.IsNotExist(err) { - if err := os.Mkdir(path, 0755); err != nil { - return fmt.Errorf("error creating path: %v", err) - } - } else if err != nil { - return fmt.Errorf("error checking path: %v", err) - } - return nil -} diff --git a/agent/installer/utils/lock.go b/agent/installer/utils/lock.go deleted file mode 100644 index 1f7e8ce54..000000000 --- a/agent/installer/utils/lock.go +++ /dev/null @@ -1,29 +0,0 @@ -package utils - -import ( - "fmt" - "os" -) - -func SetLock(lockdir string) error { - if !CheckIfPathExist(lockdir) { - file, err := os.OpenFile(lockdir, os.O_CREATE|os.O_RDWR|os.O_TRUNC, os.ModePerm) - if err != nil { - return err - } - defer file.Close() - } - return nil -} - -func RemoveLock(lockdir string) error { - if CheckIfPathExist(lockdir) { - err := os.Remove(lockdir) - if err != nil { - return err - } - } else { - return fmt.Errorf("lock file %s not exists", lockdir) - } - return nil -} diff --git a/agent/installer/utils/logger.go b/agent/installer/utils/logger.go deleted file mode 100644 index e91de3c1f..000000000 --- a/agent/installer/utils/logger.go +++ /dev/null @@ -1,22 +0,0 @@ -package utils - -import ( - "sync" - - "github.com/threatwinds/logger" -) - -var ( - installerLogger *logger.Logger - loggerOnceInstance sync.Once -) - -// CreateLogger returns a single instance of a Logger configured to save logs to a rotating file. -func CreateLogger(filename string) *logger.Logger { - loggerOnceInstance.Do(func() { - installerLogger = logger.NewLogger( - &logger.Config{Format: "text", Level: 100, Output: filename, Retries: 3, Wait: 5}, - ) - }) - return installerLogger -} diff --git a/agent/installer/utils/os.go b/agent/installer/utils/os.go deleted file mode 100644 index 3fd7dff40..000000000 --- a/agent/installer/utils/os.go +++ /dev/null @@ -1,30 +0,0 @@ -package utils - -import ( - "fmt" - "os/exec" - "strings" -) - -func DetectLinuxFamily() (string, error) { - var pmCommands map[string]string = map[string]string{ - "debian": "apt list", - "rhel": "yum list", - } - - for dist, command := range pmCommands { - cmd := strings.Split(command, " ") - var err error - - if len(cmd) > 1 { - _, err = exec.Command(cmd[0], cmd[1:]...).Output() - } else { - _, err = exec.Command(cmd[0]).Output() - } - - if err == nil { - return dist, nil - } - } - return "", fmt.Errorf("unknown distribution") -} diff --git a/agent/installer/utils/ports.go b/agent/installer/utils/ports.go deleted file mode 100644 index 9f17c01b4..000000000 --- a/agent/installer/utils/ports.go +++ /dev/null @@ -1,19 +0,0 @@ -package utils - -import ( - "fmt" - "net" - "time" -) - -func IsPortOpen(ip, port string) bool { - for i := 0; i < 3; i++ { - conn, err := net.DialTimeout("tcp", fmt.Sprintf("%s:%s", ip, port), 5*time.Second) - if err == nil { - defer conn.Close() - return true - } - time.Sleep(5 * time.Second) - } - return false -} diff --git a/agent/installer/utils/process.go b/agent/installer/utils/process.go deleted file mode 100644 index 124a3adf1..000000000 --- a/agent/installer/utils/process.go +++ /dev/null @@ -1,55 +0,0 @@ -package utils - -import ( - "os/exec" - "runtime" - "strings" -) - -// IsProcessRunning checks if a process is active -func IsProcessRunning(processName string) (bool, error) { - var cmd *exec.Cmd - if runtime.GOOS == "windows" { - cmd = exec.Command("tasklist") - } else { - cmd = exec.Command("ps", "aux") - } - - output, err := cmd.Output() - if err != nil { - return false, err - } - - processes := strings.Split(string(output), "\n") - for _, process := range processes { - if strings.Contains(process, processName) { - return true, nil - } - } - - return false, nil -} - -// StopProcess checks if a process is active, if so it stops it -func StopProcess(processName string) error { - running, err := IsProcessRunning(processName) - if err != nil { - return err - } - - if running { - var cmd *exec.Cmd - if runtime.GOOS == "windows" { - cmd = exec.Command("taskkill", "/IM", processName, "/F") - } else { - cmd = exec.Command("pkill", processName) - } - - err := cmd.Run() - if err != nil { - return err - } - } - - return nil -} diff --git a/agent/installer/utils/req.go b/agent/installer/utils/req.go deleted file mode 100644 index 7b3a88ca6..000000000 --- a/agent/installer/utils/req.go +++ /dev/null @@ -1,50 +0,0 @@ -package utils - -import ( - "bytes" - "crypto/tls" - "encoding/json" - "io" - "net/http" -) - -func DoReq[response any](url string, data []byte, method string, headers map[string]string, config *tls.Config) (response, int, error) { - req, err := http.NewRequest(method, url, bytes.NewBuffer(data)) - if err != nil { - return *new(response), http.StatusInternalServerError, err - } - - for k, v := range headers { - req.Header.Add(k, v) - } - - transp := &http.Transport{ - TLSClientConfig: config, - } - - client := &http.Client{Transport: transp} - - resp, err := client.Do(req) - if err != nil { - return *new(response), http.StatusInternalServerError, err - } - defer resp.Body.Close() - - body, err := io.ReadAll(resp.Body) - if err != nil { - return *new(response), http.StatusInternalServerError, err - } - - var result response - - err = json.Unmarshal(body, &result) - if err != nil { - return *new(response), http.StatusInternalServerError, err - } - - if resp.StatusCode != http.StatusAccepted && resp.StatusCode != http.StatusOK { - return *new(response), http.StatusInternalServerError, err - } - - return result, resp.StatusCode, nil -} diff --git a/agent/installer/utils/timestamp.go b/agent/installer/utils/timestamp.go deleted file mode 100644 index e33aa0f2a..000000000 --- a/agent/installer/utils/timestamp.go +++ /dev/null @@ -1,8 +0,0 @@ -package utils - -import "time" - -func GetCurrentTime() string { - t := time.Now() - return t.Format("20060102150405") -} diff --git a/agent/agent/logservice/log.pb.go b/agent/logservice/log.pb.go similarity index 99% rename from agent/agent/logservice/log.pb.go rename to agent/logservice/log.pb.go index c05bbb1fc..b1657f80e 100644 --- a/agent/agent/logservice/log.pb.go +++ b/agent/logservice/log.pb.go @@ -7,7 +7,7 @@ package logservice import ( - agent "github.com/utmstack/UTMStack/agent/agent/agent" + agent "github.com/utmstack/UTMStack/agent/agent" protoreflect "google.golang.org/protobuf/reflect/protoreflect" protoimpl "google.golang.org/protobuf/runtime/protoimpl" reflect "reflect" diff --git a/agent/agent/logservice/log_grpc.pb.go b/agent/logservice/log_grpc.pb.go similarity index 100% rename from agent/agent/logservice/log_grpc.pb.go rename to agent/logservice/log_grpc.pb.go diff --git a/agent/logservice/processor.go b/agent/logservice/processor.go new file mode 100644 index 000000000..009081132 --- /dev/null +++ b/agent/logservice/processor.go @@ -0,0 +1,190 @@ +package logservice + +import ( + "bufio" + context "context" + "fmt" + "os" + "path/filepath" + "strings" + "sync" + "time" + + "github.com/utmstack/UTMStack/agent/agent" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/conn" + "github.com/utmstack/UTMStack/agent/utils" + codes "google.golang.org/grpc/codes" + status "google.golang.org/grpc/status" +) + +type LogProcessor struct { + connErrWritten bool + sendErrWritten bool +} + +type LogPipe struct { + Src string + Logs []string +} + +var ( + processor LogProcessor + processorOnce sync.Once + LogQueue = make(chan LogPipe, 1000) + MinutesForCleanLog = 10080 + MinutesForReportLogsCounted = time.Duration(5 * time.Minute) + timeToSleep = 10 * time.Second + logsProcessCounter = map[string]int{} +) + +func GetLogProcessor() LogProcessor { + processorOnce.Do(func() { + processor = LogProcessor{ + connErrWritten: false, + sendErrWritten: false, + } + }) + return processor +} + +func (l *LogProcessor) ProcessLogs(cnf *config.Config, ctx context.Context) { + go func() { + for { + time.Sleep(MinutesForReportLogsCounted) + SaveCountedLogs() + logsProcessCounter = map[string]int{} + } + }() + + for { + ctxEof, cancelEof := context.WithCancel(context.Background()) + connection, err := conn.GetCorrelationConnection(cnf) + if err != nil { + if !l.connErrWritten { + utils.Logger.ErrorF("error connecting to Correlation: %v", err) + l.connErrWritten = true + } + time.Sleep(10 * time.Second) + continue + } + + client := NewLogServiceClient(connection) + l.connErrWritten = false + l.processLogs(client, ctxEof, cancelEof) + } +} + +func (l *LogProcessor) processLogs(client LogServiceClient, ctx context.Context, cancel context.CancelFunc) { + invalidKeyCounter := 0 + + for { + select { + case <-ctx.Done(): + utils.Logger.Info("LogProcessor: Context done, exiting...") + return + case newLog := <-LogQueue: + rcv, err := client.ProcessLogs(ctx, &LogMessage{Type: agent.ConnectorType_AGENT, LogType: newLog.Src, Data: newLog.Logs}) + if err != nil { + if strings.Contains(err.Error(), "EOF") { + time.Sleep(timeToSleep) + cancel() + return + } + st, ok := status.FromError(err) + if ok && (st.Code() == codes.Unavailable || st.Code() == codes.Canceled) { + if !l.sendErrWritten { + utils.Logger.ErrorF("failed to send log: %v", err) + l.sendErrWritten = true + } + time.Sleep(timeToSleep) + cancel() + return + } else { + if !l.sendErrWritten { + utils.Logger.ErrorF("failed to send log: %v ", err) + l.sendErrWritten = true + } + time.Sleep(timeToSleep) + continue + } + } else if !rcv.Received { + utils.Logger.ErrorF("Error sending logs to Log Auth Proxy: %s", rcv.Message) + if strings.Contains(rcv.Message, "invalid agent key") { + invalidKeyCounter++ + if invalidKeyCounter >= 20 { + utils.Logger.Info("Uninstalling agent: reason: agent has been removed from the panel...") + err := agent.UninstallAll() + if err != nil { + utils.Logger.ErrorF("Error uninstalling agent: %s", err) + } + } + } else { + invalidKeyCounter = 0 + } + + time.Sleep(timeToSleep) + continue + } + + l.sendErrWritten = false + logsProcessCounter[newLog.Src] += len(newLog.Logs) + invalidKeyCounter = 0 + } + + } +} + +func SaveCountedLogs() { + path := utils.GetMyPath() + filePath := filepath.Join(path, "logs_process") + logFile := filepath.Join(filePath, "processed_logs.txt") + utils.CreatePathIfNotExist(filePath) + + file, err := os.OpenFile(logFile, os.O_RDWR|os.O_CREATE|os.O_APPEND, 0666) + if err != nil { + utils.Logger.ErrorF("error opening processed_logs.txt file: %s", err) + return + } + defer file.Close() + + var firstLogTime time.Time + var firstLine string + scanner := bufio.NewScanner(file) + for scanner.Scan() { + firstLine = scanner.Text() + break + } + + if firstLine != "" { + firstLogTime, err = time.Parse("2006/01/02 15:04:05.9999999 -0700 MST", strings.Split(firstLine, " - ")[0]) + if err != nil { + utils.Logger.ErrorF("error parsing first log time: %s", err) + return + } + + if !firstLogTime.IsZero() && time.Since(firstLogTime).Minutes() >= float64(MinutesForCleanLog) { + file.Close() + if err := os.Remove(logFile); err != nil { + utils.Logger.ErrorF("error removing processed_logs.txt file: %s", err) + return + } + file, err = os.OpenFile(logFile, os.O_RDWR|os.O_CREATE|os.O_APPEND, 0666) + if err != nil { + utils.Logger.ErrorF("error opening processed_logs.txt file: %s", err) + return + } + } + } + + for name, counter := range logsProcessCounter { + if counter > 0 { + _, err = file.WriteString(fmt.Sprintf("%v - %d logs from %s have been processed\n", time.Now().Format("2006/01/02 15:04:05.9999999 -0700 MST"), counter, name)) + if err != nil { + utils.Logger.ErrorF("error writing to processed_logs.txt file: %s", err) + continue + } + } + } + +} diff --git a/agent/main.go b/agent/main.go new file mode 100644 index 000000000..cdd84a7c7 --- /dev/null +++ b/agent/main.go @@ -0,0 +1,183 @@ +package main + +import ( + "fmt" + "os" + "path/filepath" + "time" + + pb "github.com/utmstack/UTMStack/agent/agent" + "github.com/utmstack/UTMStack/agent/collectors" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/modules" + "github.com/utmstack/UTMStack/agent/serv" + "github.com/utmstack/UTMStack/agent/updates" + "github.com/utmstack/UTMStack/agent/utils" +) + +func main() { + utils.InitLogger(config.ServiceLogFile) + + if len(os.Args) > 1 { + arg := os.Args[1] + + isInstalled, err := utils.CheckIfServiceIsInstalled("UTMStackAgent") + if err != nil { + fmt.Println("Error checking if service is installed: ", err) + os.Exit(1) + } + if arg != "install" && !isInstalled { + fmt.Println("UTMStackAgent service is not installed") + os.Exit(1) + } else if arg == "install" && isInstalled { + fmt.Println("UTMStackAgent service is already installed") + os.Exit(1) + } + + switch arg { + case "run": + serv.RunService() + case "install": + utils.PrintBanner() + fmt.Println("Installing UTMStackAgent service ...") + + cnf, utmKey := config.GetInitialConfig() + + fmt.Print("Checking server connection ... ") + if err := utils.ArePortsReachable(cnf.Server, config.AgentManagerPort, config.LogAuthProxyPort, config.DependenciesPort); err != nil { + fmt.Println("\nError trying to connect to server: ", err) + os.Exit(1) + } + fmt.Println("[OK]") + + fmt.Print("Creating certificates ... ") + certsPath := filepath.Join(utils.GetMyPath(), "certs") + err = utils.CreatePathIfNotExist(certsPath) + if err != nil { + fmt.Println("\nError creating certs path: ", err) + os.Exit(1) + } + err = utils.GenerateCerts(certsPath) + if err != nil { + fmt.Println("\nError generating certs: ", err) + os.Exit(1) + } + fmt.Println("[OK]") + + fmt.Print("Downloading dependencies ... ") + if err := updates.DownloadFirstDependencies(cnf.Server, utmKey, cnf.SkipCertValidation); err != nil { + fmt.Println("\nError downloading dependencies: ", err) + os.Exit(1) + } + fmt.Println("[OK]") + + fmt.Print("Configuring agent ... ") + err = pb.RegisterAgent(cnf, utmKey) + if err != nil { + fmt.Println("\nError registering agent: ", err) + os.Exit(1) + } + if err = config.SaveConfig(cnf); err != nil { + fmt.Println("\nError saving config: ", err) + os.Exit(1) + } + if err = modules.ConfigureCollectorFirstTime(); err != nil { + fmt.Println("\nError configuring collector: ", err) + os.Exit(1) + } + if err = collectors.InstallCollectors(); err != nil { + fmt.Println("\nError installing collectors: ", err) + os.Exit(1) + } + fmt.Println("[OK]") + + fmt.Print(("Creating service ... ")) + serv.InstallService() + fmt.Println("[OK]") + fmt.Println("UTMStackAgent service installed correctly") + + case "enable-integration", "disable-integration": + fmt.Println("Changing integration status ...") + integration := os.Args[2] + proto := os.Args[3] + + port, err := modules.ChangeIntegrationStatus(integration, proto, (arg == "enable-integration")) + if err != nil { + fmt.Println("Error trying to change integration status: ", err) + os.Exit(1) + } + fmt.Printf("Action %s %s %s correctly in port %s\n", arg, integration, proto, port) + time.Sleep(5 * time.Second) + + case "change-port": + fmt.Println("Changing integration port ...") + integration := os.Args[2] + proto := os.Args[3] + port := os.Args[4] + + old, err := modules.ChangePort(integration, proto, port) + if err != nil { + fmt.Println("Error trying to change integration port: ", err) + os.Exit(1) + } + fmt.Printf("Port changed correctly from %s to %s\n", old, port) + time.Sleep(5 * time.Second) + + case "uninstall": + fmt.Println("Uninstalling UTMStackAgent service ...") + + cnf, err := config.GetCurrentConfig() + if err != nil { + fmt.Println("Error getting config: ", err) + os.Exit(1) + } + + fmt.Print("Deleting agent ... ") + if err = pb.DeleteAgent(cnf); err != nil { + utils.Logger.ErrorF("error deleting agent: %v", err) + } + if err = collectors.UninstallCollectors(); err != nil { + utils.Logger.Fatal("error uninstalling collectors: %v", err) + } + os.Remove(config.ConfigurationFile) + + serv.UninstallService() + utils.Logger.Info("UTMStackAgent service uninstalled correctly") + os.Exit(1) + case "help": + Help() + default: + fmt.Println("unknown option") + } + } else { + serv.RunService() + } +} + +func Help() { + fmt.Println("### UTMStackAgent ###") + fmt.Println("Usage:") + fmt.Println(" To run the service: ./utmstack_agent run") + fmt.Println(" To install the service: ./utmstack_agent install") + fmt.Println(" To enable integration: ./utmstack_agent enable-integration ") + fmt.Println(" To disable integration: ./utmstack_agent disable-integration ") + fmt.Println(" To change integration port: ./utmstack_agent change-port ") + fmt.Println(" To uninstall the service: ./utmstack_agent uninstall") + fmt.Println(" For help (this message): ./utmstack_agent help") + fmt.Println() + fmt.Println("Options:") + fmt.Println(" run Run the UTMStackAgent service") + fmt.Println(" install Install the UTMStackAgent service") + fmt.Println(" enable-integration Enable integration for a specific and ") + fmt.Println(" disable-integration Disable integration for a specific and ") + fmt.Println(" change-port Change the port for a specific and to ") + fmt.Println(" uninstall Uninstall the UTMStackAgent service") + fmt.Println(" help Display this help message") + fmt.Println() + fmt.Println("Note:") + fmt.Println(" - Make sure to run commands with appropriate permissions.") + fmt.Println(" - All commands require administrative privileges.") + fmt.Println(" - For detailed logs, check the service log file.") + fmt.Println() + os.Exit(0) +} diff --git a/agent/models/version.go b/agent/models/version.go new file mode 100644 index 000000000..ed01f06e4 --- /dev/null +++ b/agent/models/version.go @@ -0,0 +1,5 @@ +package models + +type Version struct { + Version string `json:"version"` +} diff --git a/agent/agent/modules/configuration.go b/agent/modules/configuration.go similarity index 50% rename from agent/agent/modules/configuration.go rename to agent/modules/configuration.go index cb90ec591..bbf527d32 100644 --- a/agent/agent/modules/configuration.go +++ b/agent/modules/configuration.go @@ -4,9 +4,10 @@ import ( "fmt" "net" "os" + "strings" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/utils" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/utils" ) type Port struct { @@ -23,34 +24,20 @@ type CollectorConfiguration struct { Integrations map[string]Integration `json:"integrations"` } -type ProtocolListenOld struct { - Enabled bool `json:"enabled"` - UDP string `json:"UDP,omitempty"` - TCP string `json:"TCP,omitempty"` - TLS string `json:"TLS,omitempty"` -} - -type CollectorConfigurationOld struct { - LogCollectorIsenabled bool `json:"log_collector_enabled"` - Integrations map[string]ProtocolListenOld `json:"integrations"` -} - func ReadCollectorConfig() (CollectorConfiguration, error) { cnf := CollectorConfiguration{} - if !utils.CheckIfPathExist(configuration.GetCollectorConfigPath()) { - cnfOld := CollectorConfigurationOld{} - err := utils.ReadJson(configuration.GetCollectorConfigPathOld(), &cnfOld) + if !utils.CheckIfPathExist(config.CollectorFileName) { + err := utils.ReadJson(config.CollectorFileNameOld, &cnf) if err != nil { return CollectorConfiguration{}, err } - cnf = MigrateOldConfig(cnfOld) - err = WriteCollectorConfig(cnf.Integrations, configuration.GetCollectorConfigPath()) + err = WriteCollectorConfig(cnf.Integrations, config.CollectorFileName) if err != nil { return CollectorConfiguration{}, err } - os.Remove(configuration.GetCollectorConfigPathOld()) + os.Remove(config.CollectorFileNameOld) } else { - err := utils.ReadJson(configuration.GetCollectorConfigPath(), &cnf) + err := utils.ReadJson(config.CollectorFileName, &cnf) if err != nil { return cnf, err } @@ -61,7 +48,7 @@ func ReadCollectorConfig() (CollectorConfiguration, error) { func ConfigureCollectorFirstTime() error { integrations := make(map[string]Integration) - for logTyp, ports := range configuration.ProtoPorts { + for logTyp, ports := range config.ProtoPorts { newIntegration := Integration{} newIntegration.TCP.IsListen = false newIntegration.TCP.Port = ports.TCP @@ -69,7 +56,7 @@ func ConfigureCollectorFirstTime() error { newIntegration.UDP.Port = ports.UDP integrations[string(logTyp)] = newIntegration } - return WriteCollectorConfig(integrations, configuration.GetCollectorConfigPath()) + return WriteCollectorConfig(integrations, config.CollectorFileName) } func ChangeIntegrationStatus(logTyp string, proto string, isEnabled bool) (string, error) { @@ -82,7 +69,7 @@ func ChangeIntegrationStatus(logTyp string, proto string, isEnabled bool) (strin if proto != "tcp" && proto != "udp" { return "", fmt.Errorf("invalid protocol: %s", proto) } - if valid := configuration.ValidateModuleType(configuration.LogType(logTyp)); valid == "nil" { + if valid := config.ValidateModuleType(logTyp); valid == "nil" { return "", fmt.Errorf("invalid integration: %s", logTyp) } @@ -97,7 +84,7 @@ func ChangeIntegrationStatus(logTyp string, proto string, isEnabled bool) (strin } cnf.Integrations[logTyp] = integration - return port, WriteCollectorConfig(cnf.Integrations, configuration.GetCollectorConfigPath()) + return port, WriteCollectorConfig(cnf.Integrations, config.CollectorFileName) } func ChangePort(logTyp string, proto string, port string) (string, error) { @@ -110,11 +97,11 @@ func ChangePort(logTyp string, proto string, port string) (string, error) { if proto != "tcp" && proto != "udp" { return "", fmt.Errorf("invalid protocol: %s", proto) } - if valid := configuration.ValidateModuleType(configuration.LogType(logTyp)); valid == "nil" { + if valid := config.ValidateModuleType(logTyp); valid == "nil" { return "", fmt.Errorf("invalid integration: %s", logTyp) } - if changeValid := ValidateChangeInPort(port, configuration.LogType(logTyp)); !changeValid { - return "", fmt.Errorf("change in port %s protocol %s not allowed for %s or out range %s-%s", port, proto, logTyp, configuration.PortRangeMin, configuration.PortRangeMax) + if changeValid := ValidateChangeInPort(port, logTyp); !changeValid { + return "", fmt.Errorf("change in port %s protocol %s not allowed for %s or out range %s-%s", port, proto, logTyp, config.PortRangeMin, config.PortRangeMax) } if !IsPortAvailable(port, proto, &cnf, logTyp) { return "", fmt.Errorf("port %s is already in use", port) @@ -131,52 +118,69 @@ func ChangePort(logTyp string, proto string, port string) (string, error) { } cnf.Integrations[logTyp] = integration - return old, WriteCollectorConfig(cnf.Integrations, configuration.GetCollectorConfigPath()) + return old, WriteCollectorConfig(cnf.Integrations, config.CollectorFileName) } func IsPortAvailable(port string, proto string, cnf *CollectorConfiguration, currentIntegration string) bool { - for integration, config := range cnf.Integrations { + for integration, integrationConfig := range cnf.Integrations { if integration != currentIntegration { - if config.TCP.Port == port || config.UDP.Port == port { + if integrationConfig.TCP.Port == port || integrationConfig.UDP.Port == port { return false } } } - ln, err := net.Listen(proto, ":"+port) + listener, err := net.Listen(proto, ":"+port) if err != nil { return false } - ln.Close() + + listener.Close() return true } -func MigrateOldConfig(old CollectorConfigurationOld) CollectorConfiguration { - integrations := make(map[string]Integration) - for logTyp, ports := range configuration.ProtoPorts { - newIntegration := Integration{} - if logTyp == "syslog" && old.LogCollectorIsenabled { - newIntegration.TCP.IsListen = true - } else { - newIntegration.TCP.IsListen = false +func WriteCollectorConfig(integrations map[string]Integration, filename string) error { + fileContent := "{\n \"integrations\": {\n" + for name, integration := range integrations { + fileContent += fmt.Sprintf(" \"%s\": {\n", name) + if integration.TCP.Port != "" { + fileContent += fmt.Sprintf(" \"tcp_port\": {\"enabled\": %t, \"value\": \"%s\"},\n", integration.TCP.IsListen, integration.TCP.Port) } - newIntegration.TCP.Port = ports.TCP - newIntegration.UDP.IsListen = false - newIntegration.UDP.Port = ports.UDP - integrations[string(logTyp)] = newIntegration + if integration.UDP.Port != "" { + fileContent += fmt.Sprintf(" \"udp_port\": {\"enabled\": %t, \"value\": \"%s\"},\n", integration.UDP.IsListen, integration.UDP.Port) + } + if strings.HasSuffix(fileContent, ",\n") { + fileContent = fileContent[:len(fileContent)-2] + "\n" + } + fileContent += " },\n" + } + if strings.HasSuffix(fileContent, ",\n") { + fileContent = fileContent[:len(fileContent)-2] + "\n" } + fileContent += " }\n}\n" - for logTyp, port := range old.Integrations { - if _, ok := integrations[logTyp]; ok { - if old.LogCollectorIsenabled && port.Enabled { - integration := integrations[logTyp] - integration.TCP.IsListen = true - integration.UDP.IsListen = false - integrations[logTyp] = integration - } - } + err := os.WriteFile(filename, []byte(fileContent), 0644) + if err != nil { + return err } - return CollectorConfiguration{Integrations: integrations} + return nil +} + +func WriteCollectorConfigFromModules(mod []Module, filename string) error { + integrations := make(map[string]Integration) + for _, m := range mod { + integrations[string(m.GetDataType())] = Integration{ + TCP: Port{ + IsListen: m.IsPortListen("tcp"), + Port: m.GetPort("tcp"), + }, + UDP: Port{ + IsListen: m.IsPortListen("udp"), + Port: m.GetPort("udp"), + }, + } + } + return WriteCollectorConfig(integrations, filename) } diff --git a/agent/agent/modules/modules.go b/agent/modules/modules.go similarity index 60% rename from agent/agent/modules/modules.go rename to agent/modules/modules.go index 95610f505..0ce4eb491 100644 --- a/agent/agent/modules/modules.go +++ b/agent/modules/modules.go @@ -3,8 +3,8 @@ package modules import ( "time" - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/utils" ) const ( @@ -12,7 +12,7 @@ const ( ) var ( - moCache = []Module{} + moCache = make([]Module, 0, 10) ) type Module interface { @@ -24,26 +24,26 @@ type Module interface { DisablePort(proto string) } -func GetModule(typ configuration.LogType, h *logger.Logger) Module { - switch configuration.ValidateModuleType(typ) { +func GetModule(typ string) Module { + switch config.ValidateModuleType(typ) { case "syslog": - return GetSyslogModule(string(typ), configuration.ProtoPorts[typ], h) + return GetSyslogModule(typ, config.ProtoPorts[config.DataType(typ)]) case "netflow": - return GetNetflowModule(h) + return GetNetflowModule() default: return nil } } -func ModulesUp(h *logger.Logger) { +func StartModules() { for { time.Sleep(delayCheckSyslogCnfig) logCollectorConfig, err := ReadCollectorConfig() if err != nil { - h.Fatal("error reading collector configuration: %v", err) + utils.Logger.Fatal("error reading collector configuration: %v", err) } - for intType, config := range logCollectorConfig.Integrations { + for intType, cnf := range logCollectorConfig.Integrations { index := -1 for i, mod := range moCache { if mod.GetDataType() == intType { @@ -53,14 +53,18 @@ func ModulesUp(h *logger.Logger) { } if index == -1 { - newModule := GetModule(configuration.LogType(intType), h) + newModule := GetModule(intType) + if newModule == nil { + utils.Logger.ErrorF("error getting module %s", intType) + continue + } moCache = append(moCache, newModule) index = len(moCache) - 1 } - configs, err := processConfigs(moCache[index], config) + configs, err := processConfigs(moCache[index], cnf) if err != nil { - h.ErrorF("error processing configs: %v", err) + utils.Logger.ErrorF("error processing configs: %v", err) continue } @@ -70,13 +74,13 @@ func ModulesUp(h *logger.Logger) { switch proto { case "tcp": - port = config.TCP.Port + port = cnf.TCP.Port case "udp": - port = config.UDP.Port + port = cnf.UDP.Port } if port != "" && moCache[index].GetPort(proto) != port { - changeAllowed = ValidateChangeInPort(port, configuration.LogType(intType)) + changeAllowed = ValidateChangeInPort(port, intType) } if conf[0] { moCache[index].DisablePort(proto) @@ -87,10 +91,10 @@ func ModulesUp(h *logger.Logger) { moCache[index].EnablePort(proto) } } else { - h.Info("change in port %s protocol %s not allowed for %s or out range %s-%s", port, proto, intType, configuration.PortRangeMin, configuration.PortRangeMax) - err := WriteCollectorConfigFromModules(moCache, configuration.GetCollectorConfigPath()) + utils.Logger.Info("change in port %s protocol %s not allowed for %s or out range %s-%s", port, proto, intType, config.PortRangeMin, config.PortRangeMax) + err := WriteCollectorConfigFromModules(moCache, config.CollectorFileName) if err != nil { - h.ErrorF("error fixing collector configuration: %v", err) + utils.Logger.ErrorF("error fixing collector configuration: %v", err) continue } } @@ -131,11 +135,11 @@ func processConfigs(mod Module, cnf Integration) (map[string][]bool, error) { } // Return true if the port change is allowed -func ValidateChangeInPort(newPort string, dataType configuration.LogType) bool { - for _, logType := range configuration.ProhibitedPortsChange { - if logType == dataType { +func ValidateChangeInPort(newPort string, dataType string) bool { + for _, logType := range config.ProhibitedPortsChange { + if string(logType) == dataType { return false } } - return configuration.PortRangeMin <= newPort && newPort <= configuration.PortRangeMax + return config.PortRangeMin <= newPort && newPort <= config.PortRangeMax } diff --git a/agent/agent/modules/netflow.go b/agent/modules/netflow.go similarity index 74% rename from agent/agent/modules/netflow.go rename to agent/modules/netflow.go index 82d324938..a2b5f5560 100644 --- a/agent/agent/modules/netflow.go +++ b/agent/modules/netflow.go @@ -11,11 +11,11 @@ import ( "github.com/tehmaze/netflow" "github.com/tehmaze/netflow/session" - "github.com/threatwinds/logger" "github.com/threatwinds/validations" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/logservice" - "github.com/utmstack/UTMStack/agent/agent/parser" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/logservice" + "github.com/utmstack/UTMStack/agent/parser" + "github.com/utmstack/UTMStack/agent/utils" ) var ( @@ -31,16 +31,14 @@ type NetflowModule struct { CTX context.Context Cancel context.CancelFunc IsEnabled bool - h *logger.Logger } -func GetNetflowModule(h *logger.Logger) *NetflowModule { +func GetNetflowModule() *NetflowModule { netflowOnce.Do(func() { netflowModule = &NetflowModule{ Parser: parser.GetParser("netflow"), DataType: "netflow", IsEnabled: false, - h: h, Decoders: make(map[string]*netflow.Decoder), } }) @@ -49,12 +47,12 @@ func GetNetflowModule(h *logger.Logger) *NetflowModule { func (m *NetflowModule) EnablePort(proto string) { if proto == "udp" && !m.IsEnabled { - m.h.Info("Server %s listening in port: %s protocol: UDP", m.DataType, configuration.ProtoPorts[configuration.LogTypeNetflow].UDP) + utils.Logger.Info("Server %s listening in port: %s protocol: UDP", m.DataType, config.ProtoPorts[config.DataTypeNetflow].UDP) m.IsEnabled = true - port, err := strconv.Atoi(configuration.ProtoPorts[configuration.LogTypeNetflow].UDP) + port, err := strconv.Atoi(config.ProtoPorts[config.DataTypeNetflow].UDP) if err != nil { - m.h.ErrorF("error converting port to int: %v", err) + utils.Logger.ErrorF("error converting port to int: %v", err) return } @@ -63,7 +61,7 @@ func (m *NetflowModule) EnablePort(proto string) { IP: net.ParseIP("0.0.0.0"), }) if err != nil { - m.h.ErrorF("error listening netflow: %v", err) + utils.Logger.ErrorF("error listening netflow: %v", err) return } @@ -93,7 +91,7 @@ func (m *NetflowModule) EnablePort(proto string) { continue } - m.h.ErrorF("error connecting with netflow listener: %v", err) + utils.Logger.ErrorF("error connecting with netflow listener: %v", err) continue } @@ -106,16 +104,16 @@ func (m *NetflowModule) EnablePort(proto string) { message, err := d.Read(bytes.NewBuffer(buffer[:length])) if err != nil { - m.h.ErrorF("error decoding NetFlow message: %v", err) + utils.Logger.ErrorF("error decoding NetFlow message: %v", err) continue } logs, err := m.Parser.ProcessData(parser.NetflowObject{ Remote: addr.String(), Message: message, - }, m.h) + }) if err != nil { - m.h.ErrorF("error parsing netflow: %v", err) + utils.Logger.ErrorF("error parsing netflow: %v", err) } for _, bulk := range logs { msgChannel <- bulk @@ -128,7 +126,7 @@ func (m *NetflowModule) EnablePort(proto string) { func (m *NetflowModule) DisablePort(proto string) { if proto == "udp" && m.IsEnabled { - m.h.Info("Server %s closed in port: %s protocol: UDP", m.DataType, configuration.ProtoPorts[configuration.LogTypeNetflow].UDP) + utils.Logger.Info("Server %s closed in port: %s protocol: UDP", m.DataType, config.ProtoPorts[config.DataTypeNetflow].UDP) m.Cancel() m.Listener.Close() m.IsEnabled = false @@ -154,7 +152,7 @@ func (m *NetflowModule) SetNewPort(proto string, port string) { func (m *NetflowModule) GetPort(proto string) string { switch proto { case "udp": - return configuration.ProtoPorts[configuration.LogTypeNetflow].UDP + return config.ProtoPorts[config.DataTypeNetflow].UDP default: return "" } @@ -180,12 +178,12 @@ func (m *NetflowModule) handleConnection(logsChannel chan []string) { for _, message := range messages { msg, _, err := validations.ValidateString(message, false) if err != nil { - m.h.ErrorF("error validating string: %v: message: %s", err, message) + utils.Logger.ErrorF("error validating string: %v: message: %s", err, message) } logBatch = append(logBatch, msg) } - if len(logBatch) >= configuration.BatchCapacity { + if len(logBatch) >= config.BatchCapacity { logservice.LogQueue <- logservice.LogPipe{ Src: m.DataType, Logs: logBatch, diff --git a/agent/agent/modules/syslog.go b/agent/modules/syslog.go similarity index 75% rename from agent/agent/modules/syslog.go rename to agent/modules/syslog.go index 4dff2e904..dd559c205 100644 --- a/agent/agent/modules/syslog.go +++ b/agent/modules/syslog.go @@ -10,11 +10,11 @@ import ( "strings" "time" - "github.com/threatwinds/logger" "github.com/threatwinds/validations" - "github.com/utmstack/UTMStack/agent/agent/configuration" - "github.com/utmstack/UTMStack/agent/agent/logservice" - "github.com/utmstack/UTMStack/agent/agent/parser" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/logservice" + "github.com/utmstack/UTMStack/agent/parser" + "github.com/utmstack/UTMStack/agent/utils" ) type SyslogModule struct { @@ -22,7 +22,6 @@ type SyslogModule struct { TCPListener listenerTCP UDPListener listenerUDP Parser parser.Parser - h *logger.Logger } type listenerTCP struct { @@ -41,7 +40,7 @@ type listenerUDP struct { Port string } -func GetSyslogModule(dataType string, protoPorts configuration.ProtoPort, h *logger.Logger) *SyslogModule { +func GetSyslogModule(dataType string, protoPorts config.ProtoPort) *SyslogModule { return &SyslogModule{ DataType: dataType, TCPListener: listenerTCP{ @@ -53,7 +52,6 @@ func GetSyslogModule(dataType string, protoPorts configuration.ProtoPort, h *log Port: protoPorts.UDP, }, Parser: parser.GetParser(dataType), - h: h, } } @@ -113,18 +111,18 @@ func (m *SyslogModule) DisablePort(proto string) { func (m *SyslogModule) enableTCP() { if !m.TCPListener.IsEnabled && m.TCPListener.Port != "" { - m.h.Info("Server %s listening in port: %s protocol: TCP", m.DataType, m.TCPListener.Port) + utils.Logger.Info("Server %s listening in port: %s protocol: TCP", m.DataType, m.TCPListener.Port) m.TCPListener.IsEnabled = true listener, err := net.Listen("tcp", "0.0.0.0"+":"+m.TCPListener.Port) if err != nil { - m.h.ErrorF("error listening TCp in port %s: %v", m.TCPListener.Port, err) + utils.Logger.ErrorF("error listening TCp in port %s: %v", m.TCPListener.Port, err) return } tcpListener, ok := listener.(*net.TCPListener) if !ok { - m.h.ErrorF("Could not assert to *net.TCPListener") + utils.Logger.ErrorF("Could not assert to *net.TCPListener") return } @@ -135,7 +133,7 @@ func (m *SyslogModule) enableTCP() { defer func() { err = m.TCPListener.Listener.Close() if err != nil { - m.h.ErrorF("error closing tcp listener: %v", err) + utils.Logger.ErrorF("error closing tcp listener: %v", err) } }() for { @@ -155,7 +153,7 @@ func (m *SyslogModule) enableTCP() { continue } - m.h.ErrorF("error connecting with tcp listener: %v", err) + utils.Logger.ErrorF("error connecting with tcp listener: %v", err) continue } go m.handleConnectionTCP(conn) @@ -168,18 +166,18 @@ func (m *SyslogModule) enableTCP() { func (m *SyslogModule) enableUDP() { if !m.UDPListener.IsEnabled && m.UDPListener.Port != "" { - m.h.Info("Server %s listening in port: %s protocol: UDP\n", m.DataType, m.UDPListener.Port) + utils.Logger.Info("Server %s listening in port: %s protocol: UDP\n", m.DataType, m.UDPListener.Port) m.UDPListener.IsEnabled = true listener, err := net.ListenPacket("udp", "0.0.0.0"+":"+m.UDPListener.Port) if err != nil { - m.h.ErrorF("error listening UDP in port %s: %v", m.UDPListener.Port, err) + utils.Logger.ErrorF("error listening UDP in port %s: %v", m.UDPListener.Port, err) return } udpListener, ok := listener.(*net.UDPConn) if !ok { - m.h.ErrorF("Could not assert to *net.UDPConn") + utils.Logger.ErrorF("Could not assert to *net.UDPConn") return } @@ -195,7 +193,7 @@ func (m *SyslogModule) enableUDP() { defer func() { err = m.UDPListener.Listener.Close() if err != nil { - m.h.ErrorF("error closing udp listener: %v", err) + utils.Logger.ErrorF("error closing udp listener: %v", err) } }() for { @@ -211,28 +209,29 @@ func (m *SyslogModule) enableUDP() { return } - netOpErr, ok := err.(*net.OpError) + var netOpErr *net.OpError + ok := errors.As(err, &netOpErr) if ok && netOpErr.Timeout() { continue } - m.h.ErrorF("error connecting with udp listener: %v", err) + utils.Logger.ErrorF("error connecting with udp listener: %v", err) continue } remoteAddr := add.String() remoteAddr, _, err = net.SplitHostPort(remoteAddr) if err != nil { - m.h.ErrorF("error getting remote addr: %v", err) + utils.Logger.ErrorF("error getting remote addr: %v", err) continue } if remoteAddr == "127.0.0.1" { remoteAddr, err = os.Hostname() if err != nil { - m.h.ErrorF("error getting hostname: %v\n", err) + utils.Logger.ErrorF("error getting hostname: %v\n", err) continue } } - messageWithIP := configuration.GetMessageFormated(remoteAddr, string(buffer[:n])) + messageWithIP := config.GetMessageFormated(remoteAddr, string(buffer[:n])) msgChannel <- messageWithIP } } @@ -242,7 +241,7 @@ func (m *SyslogModule) enableUDP() { func (m *SyslogModule) disableTCP() { if m.TCPListener.IsEnabled && m.TCPListener.Port != "" { - m.h.Info("Server %s closed in port: %s protocol: TCP", m.DataType, m.TCPListener.Port) + utils.Logger.Info("Server %s closed in port: %s protocol: TCP", m.DataType, m.TCPListener.Port) m.TCPListener.Cancel() m.TCPListener.Listener.Close() m.TCPListener.IsEnabled = false @@ -251,7 +250,7 @@ func (m *SyslogModule) disableTCP() { func (m *SyslogModule) disableUDP() { if m.UDPListener.IsEnabled && m.UDPListener.Port != "" { - m.h.Info("Server %s closed in port: %s protocol: UDP", m.DataType, m.UDPListener.Port) + utils.Logger.Info("Server %s closed in port: %s protocol: UDP", m.DataType, m.UDPListener.Port) m.UDPListener.Cancel() m.UDPListener.Listener.Close() m.UDPListener.IsEnabled = false @@ -266,13 +265,13 @@ func (m *SyslogModule) handleConnectionTCP(c net.Conn) { var err error remoteAddr, _, err = net.SplitHostPort(remoteAddr) if err != nil { - m.h.ErrorF("error spliting host and port: %v", err) + utils.Logger.ErrorF("error spliting host and port: %v", err) } if remoteAddr == "127.0.0.1" { remoteAddr, err = os.Hostname() if err != nil { - m.h.ErrorF("error getting hostname: %v\n", err) + utils.Logger.ErrorF("error getting hostname: %v\n", err) } } @@ -289,10 +288,10 @@ func (m *SyslogModule) handleConnectionTCP(c net.Conn) { if err == io.EOF || err.(net.Error).Timeout() { return } - m.h.ErrorF("error reading tcp data: %v", err) + utils.Logger.ErrorF("error reading tcp data: %v", err) return } - message = configuration.GetMessageFormated(remoteAddr, message) + message = config.GetMessageFormated(remoteAddr, message) msgChannel <- message } } @@ -307,9 +306,9 @@ func (m *SyslogModule) handleMessageTCP(logsChannel chan string) { case <-ticker.C: if len(logBatch) > 0 { if m.Parser != nil { - logs, err := m.Parser.ProcessData(logBatch, m.h) + logs, err := m.Parser.ProcessData(logBatch) if err != nil { - m.h.ErrorF("error parsing data: %v", err) + utils.Logger.ErrorF("error parsing data: %v", err) continue } for typ, bulk := range logs { @@ -331,15 +330,15 @@ func (m *SyslogModule) handleMessageTCP(logsChannel chan string) { message = strings.TrimSuffix(message, "\n") message, _, err := validations.ValidateString(message, false) if err != nil { - m.h.ErrorF("error validating string: %v: message: %s", err, message) + utils.Logger.ErrorF("error validating string: %v: message: %s", err, message) } logBatch = append(logBatch, message) - if len(logBatch) == configuration.BatchCapacity { + if len(logBatch) == config.BatchCapacity { if m.Parser != nil { - logs, err := m.Parser.ProcessData(logBatch, m.h) + logs, err := m.Parser.ProcessData(logBatch) if err != nil { - m.h.ErrorF("error parsing data: %v", err) + utils.Logger.ErrorF("error parsing data: %v", err) continue } for typ, bulk := range logs { @@ -369,9 +368,9 @@ func (m *SyslogModule) handleConnectionUDP(logsChannel chan string) { case <-ticker.C: if len(logBatch) > 0 { if m.Parser != nil { - logs, err := m.Parser.ProcessData(logBatch, m.h) + logs, err := m.Parser.ProcessData(logBatch) if err != nil { - m.h.ErrorF("error parsing data: %v", err) + utils.Logger.ErrorF("error parsing data: %v", err) continue } for typ, bulk := range logs { @@ -396,15 +395,15 @@ func (m *SyslogModule) handleConnectionUDP(logsChannel chan string) { message = strings.TrimSuffix(message, "\n") message, _, err := validations.ValidateString(message, false) if err != nil { - m.h.ErrorF("error validating string: %v: message: %s", err, message) + utils.Logger.ErrorF("error validating string: %v: message: %s", err, message) } logBatch = append(logBatch, message) - if len(logBatch) == configuration.BatchCapacity { + if len(logBatch) == config.BatchCapacity { if m.Parser != nil { - logs, err := m.Parser.ProcessData(logBatch, m.h) + logs, err := m.Parser.ProcessData(logBatch) if err != nil { - m.h.ErrorF("error parsing data: %v", err) + utils.Logger.ErrorF("error parsing data: %v", err) continue } for typ, bulk := range logs { diff --git a/agent/parser/beats.go b/agent/parser/beats.go new file mode 100644 index 000000000..ed52650ba --- /dev/null +++ b/agent/parser/beats.go @@ -0,0 +1,80 @@ +package parser + +import ( + "fmt" + "regexp" + "sync" + + "github.com/threatwinds/validations" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/utils" +) + +var ( + beatsParser = BeatsParser{} + beatsParserOnce sync.Once + RegexspBeats = map[config.DataType]string{ + config.DataTypeApacheModule: `"type":"apache"|"module":"apache"`, + config.DataTypeLinuxAuditdModule: `"type":"auditd"|"module":"auditd"`, + config.DataTypeElasticsearchModule: `"type":"elasticsearch"|"module":"elasticsearch"`, + config.DataTypeKafkaModule: `"type":"kafka"|"module":"kafka"`, + config.DataTypeKibanaModule: `"type":"kibana"|"module":"kibana"`, + config.DataTypeLogstashModule: `"type":"logstash"|"module":"logstash"`, + config.DataTypeMongodbModule: `"type":"mongodb"|"module":"mongodb"`, + config.DataTypeMysqlModule: `"type":"mysql"|"module":"mysql"`, + config.DataTypeNginxModule: `"type":"nginx"|"module":"nginx"`, + config.DataTypeOsqueryModule: `"type":"osquery"|"module":"osquery"`, + config.DataTypePostgresqlModule: `"type":"postgresql"|"module":"postgresql"`, + config.DataTypeRedisModule: `"type":"redis"|"module":"redis"`, + config.DataTypeLinuxAgent: `"type":"system"|"module":"system"`, + config.DataTypeIisModule: `"type":"iis"|"module":"iis"`, + config.DataTypeTraefikModule: `"type":"traefik"|"module":"traefik"`, + config.DataTypeNatsModule: `"type":"nats"|"module":"nats"`, + config.DataTypeHaproxyModule: `"type":"haproxy"|"module":"haproxy"`, + } +) + +type BeatsParser struct{} + +func GetBeatsParser() *BeatsParser { + beatsParserOnce.Do(func() { + beatsParser = BeatsParser{} + }) + return &beatsParser +} + +func (p *BeatsParser) IdentifySource(log string) (config.DataType, error) { + for logType, regp := range RegexspBeats { + regExpCompiled, err := regexp.Compile(string(regp)) + if err != nil { + return "", err + } + if regExpCompiled.MatchString(log) { + return logType, nil + } + } + return config.DataTypeGeneric, nil +} + +func (p *BeatsParser) ProcessData(logBatch interface{}) (map[string][]string, error) { + classifiedLogs := make(map[string][]string) + batch, ok := logBatch.([]string) + if !ok { + return nil, fmt.Errorf("invalid log batch type") + } + for _, log := range batch { + if logType, err := p.IdentifySource(log); err != nil { + return nil, err + } else { + if logType != "" { + validatedLog, _, err := validations.ValidateString(log, false) + if err != nil { + utils.Logger.ErrorF("error validating log: %s: %v", log, err) + continue + } + classifiedLogs[string(logType)] = append(classifiedLogs[string(logType)], validatedLog) + } + } + } + return classifiedLogs, nil +} diff --git a/agent/agent/parser/cisco.go b/agent/parser/cisco.go similarity index 60% rename from agent/agent/parser/cisco.go rename to agent/parser/cisco.go index 8343c7421..6becc42e6 100644 --- a/agent/agent/parser/cisco.go +++ b/agent/parser/cisco.go @@ -5,17 +5,16 @@ import ( "regexp" "sync" - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/agent/configuration" + "github.com/utmstack/UTMStack/agent/config" ) var ( ciscoParser = CiscoParser{} ciscoParserOnce sync.Once - RegexspCisco = map[configuration.LogType]string{ - configuration.LogTypeCiscoAsa: `%ASA-`, - configuration.LogTypeCiscoFirepower: `%FTD-`, - configuration.LogTypeCiscoSwitch: `%(\w|_)+-((\b\w+\b-\b\w+\b-)?)(\d)-([A-Z]|_)+`, + RegexspCisco = map[config.DataType]string{ + config.DataTypeCiscoAsa: `%ASA-`, + config.DataTypeCiscoFirepower: `%FTD-`, + config.DataTypeCiscoSwitch: `%(\w|_)+-((\b\w+\b-\b\w+\b-)?)(\d)-([A-Z]|_)+`, } ) @@ -28,7 +27,7 @@ func GetCiscoParser() *CiscoParser { return &ciscoParser } -func (p *CiscoParser) IdentifySource(log string) (configuration.LogType, error) { +func (p *CiscoParser) IdentifySource(log string) (config.DataType, error) { for logType, regp := range RegexspCisco { regExpCompiled, err := regexp.Compile(string(regp)) if err != nil { @@ -38,10 +37,10 @@ func (p *CiscoParser) IdentifySource(log string) (configuration.LogType, error) return logType, nil } } - return configuration.LogTypeCiscoMeraki, nil + return config.DataTypeCiscoMeraki, nil } -func (p *CiscoParser) ProcessData(logBatch interface{}, h *logger.Logger) (map[string][]string, error) { +func (p *CiscoParser) ProcessData(logBatch interface{}) (map[string][]string, error) { classifiedLogs := make(map[string][]string) batch, ok := logBatch.([]string) if !ok { diff --git a/agent/agent/parser/netflow.go b/agent/parser/netflow.go similarity index 86% rename from agent/agent/parser/netflow.go rename to agent/parser/netflow.go index b7d0d06d1..b979c232f 100644 --- a/agent/agent/parser/netflow.go +++ b/agent/parser/netflow.go @@ -11,8 +11,7 @@ import ( "github.com/tehmaze/netflow/netflow6" "github.com/tehmaze/netflow/netflow7" "github.com/tehmaze/netflow/netflow9" - "github.com/threatwinds/logger" - pnf "github.com/utmstack/UTMStack/agent/agent/parser/netflow" + pnf "github.com/utmstack/UTMStack/agent/parser/netflow" ) var ( @@ -35,7 +34,7 @@ type NetflowObject struct { Message netflow.Message } -func (p *NetflowParser) ProcessData(logBatch interface{}, h *logger.Logger) (map[string][]string, error) { +func (p *NetflowParser) ProcessData(logBatch interface{}) (map[string][]string, error) { var metrics []pnf.Metric var remote string diff --git a/agent/agent/parser/netflow/dump.go b/agent/parser/netflow/dump.go similarity index 76% rename from agent/agent/parser/netflow/dump.go rename to agent/parser/netflow/dump.go index d3fb982cd..5184d0112 100644 --- a/agent/agent/parser/netflow/dump.go +++ b/agent/parser/netflow/dump.go @@ -5,7 +5,7 @@ import ( "reflect" "strings" - "github.com/utmstack/UTMStack/agent/agent/configuration" + "github.com/utmstack/UTMStack/agent/config" ) func Dump(metrics []Metric, remote string) []string { @@ -23,7 +23,7 @@ func Dump(metrics []Metric, remote string) []string { header := field.Tag.Get("header") kvPairs = append(kvPairs, fmt.Sprintf("%s=\"%v\"", header, value)) } - allKVPairs = append(allKVPairs, configuration.GetMessageFormated(remote, strings.Join(kvPairs, " "))) + allKVPairs = append(allKVPairs, config.GetMessageFormated(remote, strings.Join(kvPairs, " "))) } return allKVPairs } diff --git a/agent/agent/parser/netflow/ipfix.go b/agent/parser/netflow/ipfix.go similarity index 100% rename from agent/agent/parser/netflow/ipfix.go rename to agent/parser/netflow/ipfix.go diff --git a/agent/agent/parser/netflow/metrics.go b/agent/parser/netflow/metrics.go similarity index 100% rename from agent/agent/parser/netflow/metrics.go rename to agent/parser/netflow/metrics.go diff --git a/agent/agent/parser/netflow/proto.go b/agent/parser/netflow/proto.go similarity index 100% rename from agent/agent/parser/netflow/proto.go rename to agent/parser/netflow/proto.go diff --git a/agent/agent/parser/netflow/v1.go b/agent/parser/netflow/v1.go similarity index 100% rename from agent/agent/parser/netflow/v1.go rename to agent/parser/netflow/v1.go diff --git a/agent/agent/parser/netflow/v5.go b/agent/parser/netflow/v5.go similarity index 100% rename from agent/agent/parser/netflow/v5.go rename to agent/parser/netflow/v5.go diff --git a/agent/agent/parser/netflow/v6.go b/agent/parser/netflow/v6.go similarity index 100% rename from agent/agent/parser/netflow/v6.go rename to agent/parser/netflow/v6.go diff --git a/agent/agent/parser/netflow/v7.go b/agent/parser/netflow/v7.go similarity index 100% rename from agent/agent/parser/netflow/v7.go rename to agent/parser/netflow/v7.go diff --git a/agent/agent/parser/netflow/v9.go b/agent/parser/netflow/v9.go similarity index 100% rename from agent/agent/parser/netflow/v9.go rename to agent/parser/netflow/v9.go diff --git a/agent/agent/parser/parser.go b/agent/parser/parser.go similarity index 67% rename from agent/agent/parser/parser.go rename to agent/parser/parser.go index 11b992fef..b139d8573 100644 --- a/agent/agent/parser/parser.go +++ b/agent/parser/parser.go @@ -1,9 +1,7 @@ package parser -import "github.com/threatwinds/logger" - type Parser interface { - ProcessData(logBatch interface{}, h *logger.Logger) (map[string][]string, error) + ProcessData(logMessage interface{}) (map[string][]string, error) } func GetParser(typ string) Parser { diff --git a/agent/agent/protos/agent.proto b/agent/protos/agent.proto similarity index 100% rename from agent/agent/protos/agent.proto rename to agent/protos/agent.proto diff --git a/agent/agent/protos/common.proto b/agent/protos/common.proto similarity index 100% rename from agent/agent/protos/common.proto rename to agent/protos/common.proto diff --git a/agent/agent/protos/log.proto b/agent/protos/log.proto similarity index 100% rename from agent/agent/protos/log.proto rename to agent/protos/log.proto diff --git a/agent/agent/protos/ping.proto b/agent/protos/ping.proto similarity index 100% rename from agent/agent/protos/ping.proto rename to agent/protos/ping.proto diff --git a/agent/redline/README.md b/agent/redline/README.md deleted file mode 100644 index f48a76a4d..000000000 --- a/agent/redline/README.md +++ /dev/null @@ -1,5 +0,0 @@ -# UTMStack Redline Service -The UTMStack Redline service is a critical component of the UTMStack. Its primary function is to monitor the other services within the UTMStack ecosystem, ensuring they are not unexpectedly terminated. In the event that a service is stopped unexpectedly, the Redline service will trigger an alert. - -### Logging -The UTMStack Redline service logs its activities to a file located in the logs directory. The name of the log file is path/logs/utmstack_redline.log. diff --git a/agent/redline/configuration/const.go b/agent/redline/configuration/const.go deleted file mode 100644 index 4dc8b45b0..000000000 --- a/agent/redline/configuration/const.go +++ /dev/null @@ -1,32 +0,0 @@ -package configuration - -import "runtime" - -const ( - SERV_NAME = "UTMStackRedline" - SERV_LOG = "utmstack_redline.log" - SERV_LOCK_NAME = "utmstack_redline.lock" -) - -func GetServicesLock() map[string]string { - var services = map[string]string{ - "UTMStackAgent": "utmstack_agent.lock", - "UTMStackModulesLogsCollector": "utmstack_modules_collector.lock", - "UTMStackUpdater": "utmstack_updater.lock", - } - if runtime.GOOS == "windows" { - services["UTMStackWindowsLogsCollector"] = "utmstack_windows_collector.lock" - } - return services -} - -func GetAgentBin() string { - var bin string - switch runtime.GOOS { - case "windows": - bin = "utmstack_agent_service.exe" - case "linux": - bin = "utmstack_agent_service" - } - return bin -} diff --git a/agent/redline/constants/const.go b/agent/redline/constants/const.go deleted file mode 100644 index b8adb36b2..000000000 --- a/agent/redline/constants/const.go +++ /dev/null @@ -1,32 +0,0 @@ -package constants - -import "runtime" - -const ( - SERV_NAME = "UTMStackRedline" - SERV_LOG = "utmstack_redline.log" - SERV_LOCK_NAME = "utmstack_redline.lock" -) - -func GetServicesLock() map[string]string { - var services = map[string]string{ - "UTMStackAgent": "utmstack_agent.lock", - "UTMStackModulesLogsCollector": "utmstack_modules_collector.lock", - "UTMStackUpdater": "utmstack_updater.lock", - } - if runtime.GOOS == "windows" { - services["UTMStackWindowsLogsCollector"] = "utmstack_windows_collector.lock" - } - return services -} - -func GetAgentBin() string { - var bin string - switch runtime.GOOS { - case "windows": - bin = "utmstack_agent_service.exe" - case "linux": - bin = "utmstack_agent_service" - } - return bin -} diff --git a/agent/redline/go.mod b/agent/redline/go.mod deleted file mode 100644 index d26f5681d..000000000 --- a/agent/redline/go.mod +++ /dev/null @@ -1,42 +0,0 @@ -module github.com/utmstack/UTMStack/agent/redline - -go 1.22.4 - -toolchain go1.23.4 - -require ( - github.com/kardianos/service v1.2.2 - github.com/threatwinds/logger v1.1.12 -) - -require ( - github.com/bytedance/sonic v1.12.1 // indirect - github.com/bytedance/sonic/loader v0.2.0 // indirect - github.com/cloudwego/base64x v0.1.4 // indirect - github.com/cloudwego/iasm v0.2.0 // indirect - github.com/gabriel-vasile/mimetype v1.4.5 // indirect - github.com/gin-contrib/sse v0.1.0 // indirect - github.com/gin-gonic/gin v1.10.0 // indirect - github.com/go-playground/locales v0.14.1 // indirect - github.com/go-playground/universal-translator v0.18.1 // indirect - github.com/go-playground/validator/v10 v10.22.0 // indirect - github.com/goccy/go-json v0.10.3 // indirect - github.com/google/uuid v1.6.0 // indirect - github.com/json-iterator/go v1.1.12 // indirect - github.com/klauspost/cpuid/v2 v2.2.8 // indirect - github.com/leodido/go-urn v1.4.0 // indirect - github.com/mattn/go-isatty v0.0.20 // indirect - github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect - github.com/modern-go/reflect2 v1.0.2 // indirect - github.com/pelletier/go-toml/v2 v2.2.2 // indirect - github.com/twitchyliquid64/golang-asm v0.15.1 // indirect - github.com/ugorji/go/codec v1.2.12 // indirect - golang.org/x/arch v0.9.0 // indirect - golang.org/x/crypto v0.26.0 // indirect - golang.org/x/net v0.28.0 // indirect - golang.org/x/sys v0.24.0 // indirect - golang.org/x/text v0.17.0 // indirect - google.golang.org/protobuf v1.34.2 // indirect - gopkg.in/natefinch/lumberjack.v2 v2.2.1 // indirect - gopkg.in/yaml.v3 v3.0.1 // indirect -) diff --git a/agent/redline/go.sum b/agent/redline/go.sum deleted file mode 100644 index 4f9770c5c..000000000 --- a/agent/redline/go.sum +++ /dev/null @@ -1,97 +0,0 @@ -github.com/bytedance/sonic v1.12.1 h1:jWl5Qz1fy7X1ioY74WqO0KjAMtAGQs4sYnjiEBiyX24= -github.com/bytedance/sonic v1.12.1/go.mod h1:B8Gt/XvtZ3Fqj+iSKMypzymZxw/FVwgIGKzMzT9r/rk= -github.com/bytedance/sonic/loader v0.1.1/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= -github.com/bytedance/sonic/loader v0.2.0 h1:zNprn+lsIP06C/IqCHs3gPQIvnvpKbbxyXQP1iU4kWM= -github.com/bytedance/sonic/loader v0.2.0/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= -github.com/cloudwego/base64x v0.1.4 h1:jwCgWpFanWmN8xoIUHa2rtzmkd5J2plF/dnLS6Xd/0Y= -github.com/cloudwego/base64x v0.1.4/go.mod h1:0zlkT4Wn5C6NdauXdJRhSKRlJvmclQ1hhJgA0rcu/8w= -github.com/cloudwego/iasm v0.2.0 h1:1KNIy1I1H9hNNFEEH3DVnI4UujN+1zjpuk6gwHLTssg= -github.com/cloudwego/iasm v0.2.0/go.mod h1:8rXZaNYT2n95jn+zTI1sDr+IgcD2GVs0nlbbQPiEFhY= -github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= -github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/gabriel-vasile/mimetype v1.4.5 h1:J7wGKdGu33ocBOhGy0z653k/lFKLFDPJMG8Gql0kxn4= -github.com/gabriel-vasile/mimetype v1.4.5/go.mod h1:ibHel+/kbxn9x2407k1izTA1S81ku1z/DlgOW2QE0M4= -github.com/gin-contrib/sse v0.1.0 h1:Y/yl/+YNO8GZSjAhjMsSuLt29uWRFHdHYUb5lYOV9qE= -github.com/gin-contrib/sse v0.1.0/go.mod h1:RHrZQHXnP2xjPF+u1gW/2HnVO7nvIa9PG3Gm+fLHvGI= -github.com/gin-gonic/gin v1.10.0 h1:nTuyha1TYqgedzytsKYqna+DfLos46nTv2ygFy86HFU= -github.com/gin-gonic/gin v1.10.0/go.mod h1:4PMNQiOhvDRa013RKVbsiNwoyezlm2rm0uX/T7kzp5Y= -github.com/go-playground/assert/v2 v2.2.0 h1:JvknZsQTYeFEAhQwI4qEt9cyV5ONwRHC+lYKSsYSR8s= -github.com/go-playground/assert/v2 v2.2.0/go.mod h1:VDjEfimB/XKnb+ZQfWdccd7VUvScMdVu0Titje2rxJ4= -github.com/go-playground/locales v0.14.1 h1:EWaQ/wswjilfKLTECiXz7Rh+3BjFhfDFKv/oXslEjJA= -github.com/go-playground/locales v0.14.1/go.mod h1:hxrqLVvrK65+Rwrd5Fc6F2O76J/NuW9t0sjnWqG1slY= -github.com/go-playground/universal-translator v0.18.1 h1:Bcnm0ZwsGyWbCzImXv+pAJnYK9S473LQFuzCbDbfSFY= -github.com/go-playground/universal-translator v0.18.1/go.mod h1:xekY+UJKNuX9WP91TpwSH2VMlDf28Uj24BCp08ZFTUY= -github.com/go-playground/validator/v10 v10.22.0 h1:k6HsTZ0sTnROkhS//R0O+55JgM8C4Bx7ia+JlgcnOao= -github.com/go-playground/validator/v10 v10.22.0/go.mod h1:dbuPbCMFw/DrkbEynArYaCwl3amGuJotoKCe95atGMM= -github.com/goccy/go-json v0.10.3 h1:KZ5WoDbxAIgm2HNbYckL0se1fHD6rz5j4ywS6ebzDqA= -github.com/goccy/go-json v0.10.3/go.mod h1:oq7eo15ShAhp70Anwd5lgX2pLfOS3QCiwU/PULtXL6M= -github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU= -github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= -github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= -github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= -github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= -github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= -github.com/kardianos/service v1.2.2 h1:ZvePhAHfvo0A7Mftk/tEzqEZ7Q4lgnR8sGz4xu1YX60= -github.com/kardianos/service v1.2.2/go.mod h1:CIMRFEJVL+0DS1a3Nx06NaMn4Dz63Ng6O7dl0qH0zVM= -github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= -github.com/klauspost/cpuid/v2 v2.2.8 h1:+StwCXwm9PdpiEkPyzBXIy+M9KUb4ODm0Zarf1kS5BM= -github.com/klauspost/cpuid/v2 v2.2.8/go.mod h1:Lcz8mBdAVJIBVzewtcLocK12l3Y+JytZYpaMropDUws= -github.com/knz/go-libedit v1.10.1/go.mod h1:MZTVkCWyz0oBc7JOWP3wNAzd002ZbM/5hgShxwh4x8M= -github.com/leodido/go-urn v1.4.0 h1:WT9HwE9SGECu3lg4d/dIA+jxlljEa1/ffXKmRjqdmIQ= -github.com/leodido/go-urn v1.4.0/go.mod h1:bvxc+MVxLKB4z00jd1z+Dvzr47oO32F/QSNjSBOlFxI= -github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY= -github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y= -github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= -github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= -github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM= -github.com/pelletier/go-toml/v2 v2.2.2/go.mod h1:1t835xjRzz80PqgE6HHgN2JOsmgYu/h4qDAS4n929Rs= -github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= -github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= -github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= -github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw= -github.com/stretchr/objx v0.5.0/go.mod h1:Yh+to48EsGEfYuaHDzXPcE3xhTkx73EhmCGUpEOglKo= -github.com/stretchr/objx v0.5.2/go.mod h1:FRsXN1f5AsAjCGJKqEizvkpNtU+EGNCLh3NxZ/8L+MA= -github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= -github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU= -github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o6fzry7u4= -github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= -github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= -github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= -github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= -github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= -github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= -github.com/ugorji/go/codec v1.2.12/go.mod h1:UNopzCgEMSXjBc6AOMqYvWC1ktqTAfzJZUZgYf6w6lg= -golang.org/x/arch v0.9.0 h1:ub9TgUInamJ8mrZIGlBG6/4TqWeMszd4N8lNorbrr6k= -golang.org/x/arch v0.9.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= -golang.org/x/crypto v0.26.0 h1:RrRspgV4mU+YwB4FYnuBoKsUapNIL5cohGAmSH3azsw= -golang.org/x/crypto v0.26.0/go.mod h1:GY7jblb9wI+FOo5y8/S2oY4zWP07AkOJ4+jxCqdqn54= -golang.org/x/net v0.28.0 h1:a9JDOJc5GMUJ0+UDqmLT86WiEy7iWyIhz8gz8E4e5hE= -golang.org/x/net v0.28.0/go.mod h1:yqtgsTWOOnlGLG9GFRrK3++bGOUEkNBoHZc8MEDWPNg= -golang.org/x/sys v0.0.0-20201015000850-e3ed0017c211/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.24.0 h1:Twjiwq9dn6R1fQcyiK+wQyHWfaz/BJB+YIpzU/Cv3Xg= -golang.org/x/sys v0.24.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/text v0.17.0 h1:XtiM5bkSOt+ewxlOE/aE/AKEHibwj/6gvWMl9Rsh0Qc= -golang.org/x/text v0.17.0/go.mod h1:BuEKDfySbSR4drPmRPG/7iBdf8hvFMuRexcpahXilzY= -golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= -golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= -google.golang.org/protobuf v1.34.2 h1:6xV6lTsCfpGD21XK49h7MhtcApnLqkfYgPcdHftf6hg= -google.golang.org/protobuf v1.34.2/go.mod h1:qYOHts0dSfpeUzUFpOMr/WGzszTmLH+DiWniOlNbLDw= -gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= -gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/natefinch/lumberjack.v2 v2.2.1 h1:bBRl1b0OH9s/DuPhuXpNl+VtCaJXFZ5/uEFST95x9zc= -gopkg.in/natefinch/lumberjack.v2 v2.2.1/go.mod h1:YD8tP3GAjkrDg1eZH7EGmyESg/lsYskCTPBJVb9jqSc= -gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= -gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -nullprogram.com/x/optparse v1.0.0/go.mod h1:KdyPE+Igbe0jQUrVfMqDMeJQIJZEuyV7pjYmp6pbG50= diff --git a/agent/redline/main.go b/agent/redline/main.go deleted file mode 100644 index d5ac6cb30..000000000 --- a/agent/redline/main.go +++ /dev/null @@ -1,46 +0,0 @@ -package main - -import ( - "fmt" - "log" - "os" - "path/filepath" - - "github.com/utmstack/UTMStack/agent/redline/configuration" - "github.com/utmstack/UTMStack/agent/redline/serv" - "github.com/utmstack/UTMStack/agent/redline/utils" -) - -func main() { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - log.Fatalf("Failed to get current path: %v", err) - } - - // Configuring log saving - var h = utils.CreateLogger(filepath.Join(path, "logs", configuration.SERV_LOG)) - - if len(os.Args) > 1 { - arg := os.Args[1] - switch arg { - case "run": - serv.RunService(h) - case "install": - h.Info("Installing UTMStack Redline service...") - serv.InstallService(h) - h.Info("UTMStack Redline service installed correctly") - - case "uninstall": - h.Info("Uninstalling UTMStack Redline service...") - - serv.UninstallService(h) - h.Info("UTMStack Redline service uninstalled correctly") - os.Exit(0) - default: - fmt.Println("unknown option") - } - } else { - serv.RunService(h) - } -} diff --git a/agent/redline/protector/protector.go b/agent/redline/protector/protector.go deleted file mode 100644 index b07ac9ba3..000000000 --- a/agent/redline/protector/protector.go +++ /dev/null @@ -1,66 +0,0 @@ -package protector - -import ( - "fmt" - "path/filepath" - "runtime" - "time" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/redline/configuration" - "github.com/utmstack/UTMStack/agent/redline/utils" -) - -func ProtectService(servName, lockName string, h *logger.Logger) { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - fmt.Printf("Failed to get current path: %v", err) - h.Fatal("Failed to get current path: %v", err) - } - - bin := configuration.GetAgentBin() - - attempts := 0 - for { - if attempts >= 3 { - h.Info("%s service has been stopped", servName) - if err := utils.Execute(filepath.Join(path, bin), path, "send-log", fmt.Sprintf("%s service has been stopped", servName)); err != nil { - h.ErrorF("error checking %s: error sending log : %v", servName, err) - time.Sleep(time.Second * 5) - continue - } - if err := utils.RestartService(servName); err != nil { - h.ErrorF("error checking %s: error restarting %s service: %v", servName, servName, err) - time.Sleep(time.Second * 5) - continue - } - - h.Info("%s restarted correctly", servName) - time.Sleep(time.Second * 5) - attempts = 0 - continue - } - - if isRunning, err := utils.CheckIfServiceIsActive(servName); err != nil { - h.ErrorF("error checking if %s is running: %v", servName, err) - time.Sleep(time.Second * 5) - } else if isRunning { - time.Sleep(time.Second * 5) - continue - } - if !utils.CheckIfPathExist(filepath.Join(path, "locks", lockName)) { - attempts++ - time.Sleep(time.Second * 30) - continue - } - if lockName == "utmstack_updater.lock" && runtime.GOOS == "linux" { - err = utils.Execute(filepath.Join(path, "utmstack_updater_self"), path) - if err != nil { - h.ErrorF("error executing utmstack_updater_self: %v", err) - } - time.Sleep(time.Second * 5) - continue - } - } -} diff --git a/agent/redline/serv/config.go b/agent/redline/serv/config.go deleted file mode 100644 index 88f45a9b2..000000000 --- a/agent/redline/serv/config.go +++ /dev/null @@ -1,17 +0,0 @@ -package serv - -import ( - "github.com/kardianos/service" - "github.com/utmstack/UTMStack/agent/redline/configuration" -) - -// GetConfigServ creates and returns a pointer to a service configuration structure. -func GetConfigServ() *service.Config { - svcConfig := &service.Config{ - Name: configuration.SERV_NAME, - DisplayName: "UTMStack Redline", - Description: "UTMStack Redline Service", - } - - return svcConfig -} diff --git a/agent/redline/serv/install.go b/agent/redline/serv/install.go deleted file mode 100644 index 8f0d2d032..000000000 --- a/agent/redline/serv/install.go +++ /dev/null @@ -1,30 +0,0 @@ -package serv - -import ( - "fmt" - - "github.com/kardianos/service" - "github.com/threatwinds/logger" -) - -func InstallService(h *logger.Logger) { - svcConfig := GetConfigServ() - prg := new(program) - newService, err := service.New(prg, svcConfig) - if err != nil { - fmt.Printf("error creating new service: %v", err) - h.Fatal("error creating new service: %v", err) - } - err = newService.Install() - if err != nil { - fmt.Printf("error installing new service: %v", err) - h.Fatal("error installing new service: %v", err) - } - - // Start the service after installing it - err = newService.Start() - if err != nil { - fmt.Printf("error starting new service: %v", err) - h.Fatal("error starting new service: %v", err) - } -} diff --git a/agent/redline/serv/run.go b/agent/redline/serv/run.go deleted file mode 100644 index 1706b223a..000000000 --- a/agent/redline/serv/run.go +++ /dev/null @@ -1,19 +0,0 @@ -package serv - -import ( - "github.com/kardianos/service" - "github.com/threatwinds/logger" -) - -func RunService(h *logger.Logger) { - svcConfig := GetConfigServ() - prg := new(program) - newService, err := service.New(prg, svcConfig) - if err != nil { - h.Fatal("error creating new service: %v", err) - } - err = newService.Run() - if err != nil { - h.Fatal("error running new service: %v", err) - } -} diff --git a/agent/redline/serv/service.go b/agent/redline/serv/service.go deleted file mode 100644 index 286fc9d0d..000000000 --- a/agent/redline/serv/service.go +++ /dev/null @@ -1,54 +0,0 @@ -package serv - -import ( - "log" - "os" - "os/signal" - "path/filepath" - "syscall" - "time" - - "github.com/kardianos/service" - "github.com/utmstack/UTMStack/agent/redline/configuration" - "github.com/utmstack/UTMStack/agent/redline/protector" - "github.com/utmstack/UTMStack/agent/redline/utils" -) - -type program struct{} - -func (p *program) Start(s service.Service) error { - go p.run() - return nil -} - -func (p *program) Stop(s service.Service) error { - return nil -} - -func (p *program) run() { - path, err := utils.GetMyPath() - if err != nil { - log.Fatalf("Failed to get current path: %v\n", err) - } - - // Configuring log saving - var h = utils.CreateLogger(filepath.Join(path, "logs", configuration.SERV_LOG)) - - for { - if utils.CheckIfPathExist(filepath.Join(path, "locks", "setup.lock")) { - time.Sleep(time.Second * 5) - continue - } - break - } - - h.Info("UTMStackRedline started correctly") - for servName, lockName := range configuration.GetServicesLock() { - go protector.ProtectService(servName, lockName, h) - } - - signals := make(chan os.Signal, 1) - signal.Notify(signals, syscall.SIGINT, syscall.SIGTERM) - <-signals - -} diff --git a/agent/redline/serv/uninstall.go b/agent/redline/serv/uninstall.go deleted file mode 100644 index 689851559..000000000 --- a/agent/redline/serv/uninstall.go +++ /dev/null @@ -1,19 +0,0 @@ -package serv - -import ( - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/redline/configuration" - "github.com/utmstack/UTMStack/agent/redline/utils" -) - -func UninstallService(h *logger.Logger) { - // Uninstall service - err := utils.StopService(configuration.SERV_NAME) - if err != nil { - h.Fatal("error stopping %s: %v", configuration.SERV_NAME, err) - } - err = utils.UninstallService("%s") - if err != nil { - h.Fatal("error uninstalling %s: %v", configuration.SERV_NAME, err) - } -} diff --git a/agent/redline/utils/cmd.go b/agent/redline/utils/cmd.go deleted file mode 100644 index b1881855f..000000000 --- a/agent/redline/utils/cmd.go +++ /dev/null @@ -1,47 +0,0 @@ -package utils - -import ( - "errors" - "os/exec" - "unicode/utf8" -) - -func CleanString(s string) string { - v := make([]rune, 0, len(s)) - for i, r := range s { - if r == utf8.RuneError { - _, size := utf8.DecodeRuneInString(s[i:]) - if size == 1 { - v = append(v, '?') - continue - } - } - v = append(v, r) - } - return string(v) -} - -func ExecuteWithResult(c string, dir string, arg ...string) (string, bool) { - cmd := exec.Command(c, arg...) - - cmd.Dir = dir - if errors.Is(cmd.Err, exec.ErrDot) { - cmd.Err = nil - } - - out, err := cmd.Output() - if err != nil { - return string(out[:]) + err.Error(), true - } - - validUtf8Out := CleanString(string(out[:])) - - return validUtf8Out, false -} - -func Execute(c string, dir string, arg ...string) error { - cmd := exec.Command(c, arg...) - cmd.Dir = dir - - return cmd.Run() -} diff --git a/agent/redline/utils/files.go b/agent/redline/utils/files.go deleted file mode 100644 index 990ba483c..000000000 --- a/agent/redline/utils/files.go +++ /dev/null @@ -1,24 +0,0 @@ -package utils - -import ( - "os" - "path/filepath" -) - -// GetMyPath returns the directory path where the currently running executable is located. -// Returns a string representing the directory path, and an error if any error occurs during the process. -func GetMyPath() (string, error) { - ex, err := os.Executable() - if err != nil { - return "", err - } - exPath := filepath.Dir(ex) - return exPath, nil -} - -func CheckIfPathExist(path string) bool { - if _, err := os.Stat(path); os.IsNotExist(err) { - return false - } - return true -} diff --git a/agent/redline/utils/logger.go b/agent/redline/utils/logger.go deleted file mode 100644 index 173644bf7..000000000 --- a/agent/redline/utils/logger.go +++ /dev/null @@ -1,22 +0,0 @@ -package utils - -import ( - "sync" - - "github.com/threatwinds/logger" -) - -var ( - redlineLogger *logger.Logger - loggerOnceInstance sync.Once -) - -// CreateLogger returns a single instance of a Logger configured to save logs to a rotating file. -func CreateLogger(filename string) *logger.Logger { - loggerOnceInstance.Do(func() { - redlineLogger = logger.NewLogger( - &logger.Config{Format: "text", Level: 100, Output: filename, Retries: 3, Wait: 5}, - ) - }) - return redlineLogger -} diff --git a/agent/redline/utils/services.go b/agent/redline/utils/services.go deleted file mode 100644 index 79fd9c5a4..000000000 --- a/agent/redline/utils/services.go +++ /dev/null @@ -1,125 +0,0 @@ -package utils - -import ( - "fmt" - "runtime" - "strings" -) - -// CheckIfServiceIsActive checks if a service is active or running -func CheckIfServiceIsActive(serv string) (bool, error) { - var errB bool - var output string - - path, err := GetMyPath() - if err != nil { - return false, fmt.Errorf("error getting current path: %v", err) - } - - switch runtime.GOOS { - case "windows": - output, errB = ExecuteWithResult("sc", path, "query", serv) - case "linux": - output, errB = ExecuteWithResult("systemctl", path, "is-active", serv) - default: - return false, fmt.Errorf("unknown operating system") - } - - if errB { - return false, nil - } - - serviceStatus := strings.ToLower(strings.TrimSpace(string(output))) - if runtime.GOOS == "linux" { - return serviceStatus == "active", nil - } else if runtime.GOOS == "windows" { - return strings.Contains(serviceStatus, "running"), nil - } - - return false, fmt.Errorf("unsupported operating system") -} - -// RestartService restarts a service -func RestartService(serv string) error { - path, err := GetMyPath() - if err != nil { - return fmt.Errorf("error getting current path: %v", err) - } - - isRunning, err := CheckIfServiceIsActive(serv) - if err != nil { - return fmt.Errorf("error checking if %s service is active: %v", serv, err) - } - - switch runtime.GOOS { - case "windows": - if isRunning { - err := Execute("sc", path, "stop", serv) - if err != nil { - return fmt.Errorf("error stopping service: %v", err) - } - } - err := Execute("sc", path, "start", serv) - if err != nil { - return fmt.Errorf("error starting service: %v", err) - } - - case "linux": - if isRunning { - err := Execute("systemctl", path, "restart", serv) - if err != nil { - return fmt.Errorf("error restarting service: %v", err) - } - } else { - err := Execute("systemctl", path, "start", serv) - if err != nil { - return fmt.Errorf("error starting service: %v", err) - } - } - } - return nil -} - -func StopService(name string) error { - path, err := GetMyPath() - if err != nil { - return err - } - switch runtime.GOOS { - case "windows": - err := Execute("sc", path, "stop", name) - if err != nil { - return fmt.Errorf("error stoping service: %v", err) - } - case "linux": - err := Execute("systemctl", path, "stop", name) - if err != nil { - return fmt.Errorf("error stoping service: %v", err) - } - } - return nil -} - -func UninstallService(name string) error { - path, err := GetMyPath() - if err != nil { - return err - } - switch runtime.GOOS { - case "windows": - err := Execute("sc", path, "delete", name) - if err != nil { - return fmt.Errorf("error uninstalling service: %v", err) - } - case "linux": - err := Execute("systemctl", path, "disable", name) - if err != nil { - return fmt.Errorf("error uninstalling service: %v", err) - } - err = Execute("rm", "/etc/systemd/system/", "/etc/systemd/system/"+name+".service") - if err != nil { - return fmt.Errorf("error uninstalling service: %v", err) - } - } - return nil -} diff --git a/agent/rsrc_windows_386.syso b/agent/rsrc_windows_386.syso new file mode 100644 index 000000000..2aaa16e00 Binary files /dev/null and b/agent/rsrc_windows_386.syso differ diff --git a/agent/rsrc_windows_amd64.syso b/agent/rsrc_windows_amd64.syso new file mode 100644 index 000000000..abb2f076d Binary files /dev/null and b/agent/rsrc_windows_amd64.syso differ diff --git a/agent/self/README.md b/agent/self/README.md deleted file mode 100644 index 4298e1517..000000000 --- a/agent/self/README.md +++ /dev/null @@ -1,10 +0,0 @@ -# UTMStack Agent Service Dependency: Self-Updater -This project is a crucial dependency for the UTMStack Agent Service. It is specifically designed to handle updates for the UTMStack Updater Service. When the UTMStack Updater Service finds an update for itself, this tool allows it to uninstall and update itself seamlessly. - -### Features -Self-Updating: The primary feature of this tool is to enable the UTMStack Updater Service to update itself when an update is found. -Logging: The tool logs all its activities, which can be useful for debugging and tracking its operations. -Error Handling: The tool is designed to handle errors gracefully and log them for further analysis. - -### How it Works -The tool first gets the current path of the UTMStack Updater Service. It then configures log saving and reads data from versions.json. It selects the environment and checks if the UTMStack Updater Service is active. If it is, the service is stopped. The tool then updates the UTMStack Updater Service and restarts it. diff --git a/agent/self/config/const.go b/agent/self/config/const.go new file mode 100644 index 000000000..2d89a1ee5 --- /dev/null +++ b/agent/self/config/const.go @@ -0,0 +1,6 @@ +package config + +const ( + SERV_NAME = "UTMStackAgent" + SERV_LOG = "utmstack_updater_self.log" +) diff --git a/agent/self/config/linux_amd64.go b/agent/self/config/linux_amd64.go new file mode 100644 index 000000000..2bd4ccf23 --- /dev/null +++ b/agent/self/config/linux_amd64.go @@ -0,0 +1,8 @@ +//go:build linux && amd64 +// +build linux,amd64 + +package config + +var ( + ServiceFile = "utmstack_agent_service%s" +) diff --git a/agent/self/config/linux_arm64.go b/agent/self/config/linux_arm64.go new file mode 100644 index 000000000..35fbef145 --- /dev/null +++ b/agent/self/config/linux_arm64.go @@ -0,0 +1,8 @@ +//go:build linux && arm64 +// +build linux,arm64 + +package config + +var ( + ServiceFile = "utmstack_agent_service_arm64%s" +) diff --git a/agent/self/config/win_amd64.go b/agent/self/config/win_amd64.go new file mode 100644 index 000000000..87bcb5eea --- /dev/null +++ b/agent/self/config/win_amd64.go @@ -0,0 +1,8 @@ +//go:build windows && amd64 +// +build windows,amd64 + +package config + +var ( + ServiceFile = "utmstack_agent_service%s.exe" +) diff --git a/agent/self/config/win_arm64.go b/agent/self/config/win_arm64.go new file mode 100644 index 000000000..ccedb2f95 --- /dev/null +++ b/agent/self/config/win_arm64.go @@ -0,0 +1,8 @@ +//go:build windows && arm64 +// +build windows,arm64 + +package config + +var ( + ServiceFile = "utmstack_agent_service_arm64%s.exe" +) diff --git a/agent/self/configuration/config.go b/agent/self/configuration/config.go deleted file mode 100644 index bb2b4ceeb..000000000 --- a/agent/self/configuration/config.go +++ /dev/null @@ -1,32 +0,0 @@ -package configuration - -import ( - "os" - "path/filepath" - - "github.com/utmstack/UTMStack/agent/self/utils" -) - -type Environment struct { - Branch string `yaml:"branch"` -} - -func ReadEnv() (*Environment, error) { - var env Environment - path, err := utils.GetMyPath() - if err != nil { - return nil, err - } - - path = filepath.Join(path, "env.yml") - - if _, err = os.Stat(path); os.IsNotExist(err) { - return &Environment{Branch: "release"}, nil - } else { - err = utils.ReadYAML(path, &env) - if err != nil { - return nil, err - } - } - return &env, nil -} diff --git a/agent/self/configuration/const.go b/agent/self/configuration/const.go deleted file mode 100644 index 854fa2846..000000000 --- a/agent/self/configuration/const.go +++ /dev/null @@ -1,23 +0,0 @@ -package configuration - -import "runtime" - -const ( - SERV_NAME = "UTMStackUpdaterSelf" - SERV_LOG = "utmstack_updater_self.log" - UPDATER_SERV_NAME = "UTMStackUpdater" - UPDATER_SERV_LOCK = "utmstack_updater.lock" - Bucket = "https://cdn.utmstack.com/agent_updates/" - SERV_LOCK = "utmstack_updater.lock" -) - -func GetUpdaterBin() string { - var bin string - switch runtime.GOOS { - case "windows": - bin = "utmstack_updater_service.exe" - case "linux": - bin = "utmstack_updater_service" - } - return bin -} diff --git a/agent/self/constants/const.go b/agent/self/constants/const.go deleted file mode 100644 index cbe5cfa99..000000000 --- a/agent/self/constants/const.go +++ /dev/null @@ -1,23 +0,0 @@ -package constants - -import "runtime" - -const ( - SERV_NAME = "UTMStackUpdaterSelf" - SERV_LOG = "utmstack_updater_self.log" - UPDATER_SERV_NAME = "UTMStackUpdater" - UPDATER_SERV_LOCK = "utmstack_updater.lock" - Bucket = "https://cdn.utmstack.com/agent_updates/" - SERV_LOCK = "utmstack_updater.lock" -) - -func GetUpdaterBin() string { - var bin string - switch runtime.GOOS { - case "windows": - bin = "utmstack_updater_service.exe" - case "linux": - bin = "utmstack_updater_service" - } - return bin -} diff --git a/agent/self/go.mod b/agent/self/go.mod index d74d8737c..f9ba38c2e 100644 --- a/agent/self/go.mod +++ b/agent/self/go.mod @@ -1,13 +1,10 @@ module github.com/utmstack/UTMStack/agent/self -go 1.22.4 +go 1.23.0 toolchain go1.23.4 -require ( - github.com/threatwinds/logger v1.1.12 - gopkg.in/yaml.v2 v2.4.0 -) +require github.com/threatwinds/logger v1.2.1 require ( github.com/bytedance/sonic v1.12.1 // indirect @@ -32,10 +29,10 @@ require ( github.com/twitchyliquid64/golang-asm v0.15.1 // indirect github.com/ugorji/go/codec v1.2.12 // indirect golang.org/x/arch v0.9.0 // indirect - golang.org/x/crypto v0.26.0 // indirect - golang.org/x/net v0.28.0 // indirect - golang.org/x/sys v0.24.0 // indirect - golang.org/x/text v0.17.0 // indirect + golang.org/x/crypto v0.35.0 // indirect + golang.org/x/net v0.36.0 // indirect + golang.org/x/sys v0.30.0 // indirect + golang.org/x/text v0.22.0 // indirect google.golang.org/protobuf v1.34.2 // indirect gopkg.in/natefinch/lumberjack.v2 v2.2.1 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect diff --git a/agent/self/go.sum b/agent/self/go.sum index ec4ffc893..7e6037bf1 100644 --- a/agent/self/go.sum +++ b/agent/self/go.sum @@ -62,24 +62,24 @@ github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= +github.com/threatwinds/logger v1.2.1 h1:uN7efZaHobMX3DRi6GOPtxESPxt5xj0bNflnmgklwII= +github.com/threatwinds/logger v1.2.1/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= github.com/ugorji/go/codec v1.2.12/go.mod h1:UNopzCgEMSXjBc6AOMqYvWC1ktqTAfzJZUZgYf6w6lg= golang.org/x/arch v0.9.0 h1:ub9TgUInamJ8mrZIGlBG6/4TqWeMszd4N8lNorbrr6k= golang.org/x/arch v0.9.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= -golang.org/x/crypto v0.26.0 h1:RrRspgV4mU+YwB4FYnuBoKsUapNIL5cohGAmSH3azsw= -golang.org/x/crypto v0.26.0/go.mod h1:GY7jblb9wI+FOo5y8/S2oY4zWP07AkOJ4+jxCqdqn54= -golang.org/x/net v0.28.0 h1:a9JDOJc5GMUJ0+UDqmLT86WiEy7iWyIhz8gz8E4e5hE= -golang.org/x/net v0.28.0/go.mod h1:yqtgsTWOOnlGLG9GFRrK3++bGOUEkNBoHZc8MEDWPNg= +golang.org/x/crypto v0.35.0 h1:b15kiHdrGCHrP6LvwaQ3c03kgNhhiMgvlhxHQhmg2Xs= +golang.org/x/crypto v0.35.0/go.mod h1:dy7dXNW32cAb/6/PRuTNsix8T+vJAqvuIy5Bli/x0YQ= +golang.org/x/net v0.36.0 h1:vWF2fRbw4qslQsQzgFqZff+BItCvGFQqKzKIzx1rmoA= +golang.org/x/net v0.36.0/go.mod h1:bFmbeoIPfrw4sMHNhb4J9f6+tPziuGjq7Jk/38fxi1I= golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.24.0 h1:Twjiwq9dn6R1fQcyiK+wQyHWfaz/BJB+YIpzU/Cv3Xg= -golang.org/x/sys v0.24.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/text v0.17.0 h1:XtiM5bkSOt+ewxlOE/aE/AKEHibwj/6gvWMl9Rsh0Qc= -golang.org/x/text v0.17.0/go.mod h1:BuEKDfySbSR4drPmRPG/7iBdf8hvFMuRexcpahXilzY= +golang.org/x/sys v0.30.0 h1:QjkSwP/36a20jFYWkSue1YwXzLmsV5Gfq7Eiy72C1uc= +golang.org/x/sys v0.30.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= +golang.org/x/text v0.22.0 h1:bofq7m3/HAFvbF51jz3Q9wLg3jkvSPuiZu/pD1XwgtM= +golang.org/x/text v0.22.0/go.mod h1:YRoo4H8PVmsu+E3Ou7cqLVH8oXWIHVoX0jqUWALQhfY= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= google.golang.org/protobuf v1.34.2 h1:6xV6lTsCfpGD21XK49h7MhtcApnLqkfYgPcdHftf6hg= @@ -88,8 +88,6 @@ gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+ gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/natefinch/lumberjack.v2 v2.2.1 h1:bBRl1b0OH9s/DuPhuXpNl+VtCaJXFZ5/uEFST95x9zc= gopkg.in/natefinch/lumberjack.v2 v2.2.1/go.mod h1:YD8tP3GAjkrDg1eZH7EGmyESg/lsYskCTPBJVb9jqSc= -gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= -gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= diff --git a/agent/self/main.go b/agent/self/main.go index 9f217ef07..51f057b6a 100644 --- a/agent/self/main.go +++ b/agent/self/main.go @@ -1,64 +1,41 @@ package main import ( - "log" "path/filepath" + "time" - "github.com/utmstack/UTMStack/agent/self/configuration" + "github.com/utmstack/UTMStack/agent/self/config" "github.com/utmstack/UTMStack/agent/self/update" "github.com/utmstack/UTMStack/agent/self/utils" ) func main() { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - log.Fatalf("Failed to get current path: %v", err) - } - - // Configuring log saving - var h = utils.CreateLogger(filepath.Join(path, "logs", configuration.SERV_LOG)) + path := utils.GetMyPath() + utils.InitLogger(filepath.Join(path, "logs", config.SERV_LOG)) - // Save data from versions.json - allVersions := update.Version{} - err = utils.ReadJson(filepath.Join(path, "versions.json"), &allVersions) - if err != nil { - h.Fatal("error reading current versions.json: %v", err) - } + utils.SelfLogger.Info("Updating %s...", config.SERV_NAME) - // Select environment - env, err := configuration.ReadEnv() - if err != nil { - h.Fatal("Failed to get current path: %v", err) - } - - h.Info("Updating UTMStackUpdater...") - - if isRunning, err := utils.CheckIfServiceIsActive(configuration.UPDATER_SERV_NAME); err != nil { - h.Fatal("error checking %s service: %v", configuration.UPDATER_SERV_NAME, err) + if isRunning, err := utils.CheckIfServiceIsActive(config.SERV_NAME); err != nil { + utils.SelfLogger.Fatal("error checking %s service: %v", config.SERV_NAME, err) } else if isRunning { - err = utils.StopService(configuration.UPDATER_SERV_NAME) + err = utils.StopService(config.SERV_NAME) if err != nil { - h.Fatal("error stopping %s service: %v", configuration.UPDATER_SERV_NAME, err) + utils.SelfLogger.Fatal("error stopping %s service: %v", config.SERV_NAME, err) } - h.Info("UTMStackUpdater stopped correctly") + utils.SelfLogger.Info("%s stopped correctly", config.SERV_NAME) } - err = update.UpdateUpdaterService(allVersions.UpdaterVersion, env.Branch) - if err != nil { - h.Fatal("error downloading new %s service: %v", configuration.UPDATER_SERV_NAME, err) - } - h.Info("New UTMStackUpdater downloaded correctly") + time.Sleep(10 * time.Second) - err = utils.RestartService(configuration.UPDATER_SERV_NAME) + err := update.RunUpdate() if err != nil { - h.Fatal("error restarting %s service: %v", configuration.UPDATER_SERV_NAME, err) + utils.SelfLogger.Fatal("error updating new %s service: %v", config.SERV_NAME, err) } - h.Info("UTMStackUpdater restarted correctly") + utils.SelfLogger.Info("New %s downloaded correctly", config.SERV_NAME) - err = utils.RemoveLock(filepath.Join(path, "locks", configuration.SERV_LOCK)) + err = utils.RestartService(config.SERV_NAME) if err != nil { - h.Fatal("error removing %s: %v", configuration.SERV_LOCK, err) + utils.SelfLogger.Fatal("error restarting %s service: %v", config.SERV_NAME, err) } - h.Info("UTMStackUpdater updated correctly") + utils.SelfLogger.Info("%s updated correctly", config.SERV_NAME) } diff --git a/agent/self/rsrc_windows_386.syso b/agent/self/rsrc_windows_386.syso new file mode 100644 index 000000000..2aaa16e00 Binary files /dev/null and b/agent/self/rsrc_windows_386.syso differ diff --git a/agent/self/rsrc_windows_amd64.syso b/agent/self/rsrc_windows_amd64.syso new file mode 100644 index 000000000..abb2f076d Binary files /dev/null and b/agent/self/rsrc_windows_amd64.syso differ diff --git a/agent/self/update/schema.go b/agent/self/update/schema.go deleted file mode 100644 index 7a58ae79f..000000000 --- a/agent/self/update/schema.go +++ /dev/null @@ -1,8 +0,0 @@ -package update - -type Version struct { - MasterVersion string `json:"master_version"` - AgentVersion string `json:"agent_version"` - UpdaterVersion string `json:"updater_version"` - RedlineVersion string `json:"redline_version"` -} diff --git a/agent/self/update/update.go b/agent/self/update/update.go index c45559d3c..22011d831 100644 --- a/agent/self/update/update.go +++ b/agent/self/update/update.go @@ -2,31 +2,26 @@ package update import ( "fmt" + "os" "path/filepath" - "runtime" - "github.com/utmstack/UTMStack/agent/self/configuration" + "github.com/utmstack/UTMStack/agent/self/config" "github.com/utmstack/UTMStack/agent/self/utils" ) -func UpdateUpdaterService(version, env string) error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } +func RunUpdate() error { + path := utils.GetMyPath() - // Download new bin - bin := configuration.GetUpdaterBin() - url := configuration.Bucket + env + "/updater_service/v" + version + "/" + bin + "?time=" + utils.GetCurrentTime() - err = utils.DownloadFile(url, filepath.Join(path, bin)) + newbin := fmt.Sprintf(config.ServiceFile, "_new") + oldbin := fmt.Sprintf(config.ServiceFile, "") + err := os.Remove(filepath.Join(path, oldbin)) if err != nil { - return fmt.Errorf("error downloading new %s: %v", bin, err) + return fmt.Errorf("error removing old %s: %v", oldbin, err) } - if runtime.GOOS == "linux" { - if err = utils.Execute("chmod", path, "-R", "777", bin); err != nil { - return fmt.Errorf("error executing chmod: %v", err) - } + err = os.Rename(filepath.Join(path, newbin), filepath.Join(path, oldbin)) + if err != nil { + return fmt.Errorf("error renaming new %s: %v", newbin, err) } return nil diff --git a/agent/self/utils/delay.go b/agent/self/utils/delay.go deleted file mode 100644 index e3000ea71..000000000 --- a/agent/self/utils/delay.go +++ /dev/null @@ -1,11 +0,0 @@ -package utils - -import "time" - -func IncrementReconnectDelay(delay time.Duration, maxReconnectDelay time.Duration) time.Duration { - delay *= 2 - if delay > maxReconnectDelay { - delay = maxReconnectDelay - } - return delay -} diff --git a/agent/self/utils/download.go b/agent/self/utils/download.go deleted file mode 100644 index a0d578eb0..000000000 --- a/agent/self/utils/download.go +++ /dev/null @@ -1,51 +0,0 @@ -package utils - -import ( - "fmt" - "io" - "net/http" - "os" - "time" -) - -const ( - maxConnectionAttempts = 3 - initialReconnectDelay = 10 * time.Second - maxReconnectDelay = 60 * time.Second -) - -// DownloadFile downloads a file from a URL and saves it to disk. Returns an error on failure. -func DownloadFile(url string, fileName string) error { - connectionAttemps := 0 - reconnectDelay := initialReconnectDelay - - var resp *http.Response - var err error - - for { - if connectionAttemps >= maxConnectionAttempts { - return fmt.Errorf("error downloading file after %d attemps: %v", maxConnectionAttempts, err) - } - resp, err = http.Get(url) - if err != nil || resp.StatusCode != http.StatusOK { - if resp != nil { - resp.Body.Close() - } - connectionAttemps++ - time.Sleep(reconnectDelay) - reconnectDelay = IncrementReconnectDelay(reconnectDelay, maxReconnectDelay) - continue - } - break - } - defer resp.Body.Close() - - out, err := os.Create(fileName) - if err != nil { - return err - } - defer out.Close() - - _, err = io.Copy(out, resp.Body) - return err -} diff --git a/agent/self/utils/files.go b/agent/self/utils/files.go index 805cc34e8..24baf7dae 100644 --- a/agent/self/utils/files.go +++ b/agent/self/utils/files.go @@ -1,56 +1,15 @@ package utils import ( - "encoding/json" "os" "path/filepath" - - "gopkg.in/yaml.v2" ) -// GetMyPath returns the directory path where the currently running executable is located. -// Returns a string representing the directory path, and an error if any error occurs during the process. -func GetMyPath() (string, error) { +func GetMyPath() string { ex, err := os.Executable() if err != nil { - return "", err + return "" } exPath := filepath.Dir(ex) - return exPath, nil -} - -// ReadJson reads the json data from the specified file URL and unmarshal it into the provided result interface{}. -// Returns an error if any error occurs during the process. -func ReadJson(fileName string, data interface{}) error { - content, err := os.ReadFile(fileName) - if err != nil { - return err - } - err = json.Unmarshal(content, data) - if err != nil { - return err - } - return nil -} - -// ReadYAML reads the YAML data from the specified file URL and deserializes it into the provided result interface{}. -// Returns an error if any error occurs during the process. -func ReadYAML(path string, result interface{}) error { - file, err := os.Open(path) - if err != nil { - return err - } - defer file.Close() - d := yaml.NewDecoder(file) - if err := d.Decode(result); err != nil { - return err - } - return nil -} - -func CheckIfPathExist(path string) bool { - if _, err := os.Stat(path); os.IsNotExist(err) { - return false - } - return true + return exPath } diff --git a/agent/self/utils/lock.go b/agent/self/utils/lock.go deleted file mode 100644 index 965dba81c..000000000 --- a/agent/self/utils/lock.go +++ /dev/null @@ -1,18 +0,0 @@ -package utils - -import ( - "fmt" - "os" -) - -func RemoveLock(lockdir string) error { - if CheckIfPathExist(lockdir) { - err := os.Remove(lockdir) - if err != nil { - return err - } - } else { - return fmt.Errorf("lock file %s not exists", lockdir) - } - return nil -} diff --git a/agent/self/utils/logger.go b/agent/self/utils/logger.go index 050144d20..e2e8c7fdf 100644 --- a/agent/self/utils/logger.go +++ b/agent/self/utils/logger.go @@ -7,16 +7,14 @@ import ( ) var ( - selfLogger *logger.Logger + SelfLogger *logger.Logger loggerOnceInstance sync.Once ) -// CreateLogger returns a single instance of a Logger configured to save logs to a rotating file. -func CreateLogger(filename string) *logger.Logger { +func InitLogger(filename string) { loggerOnceInstance.Do(func() { - selfLogger = logger.NewLogger( + SelfLogger = logger.NewLogger( &logger.Config{Format: "text", Level: 100, Output: filename, Retries: 3, Wait: 5}, ) }) - return selfLogger } diff --git a/agent/self/utils/services.go b/agent/self/utils/services.go index 38f7b37cd..b8f273306 100644 --- a/agent/self/utils/services.go +++ b/agent/self/utils/services.go @@ -6,15 +6,10 @@ import ( "strings" ) -// CheckIfServiceIsActive checks if a service is active or running func CheckIfServiceIsActive(serv string) (bool, error) { var errB bool var output string - - path, err := GetMyPath() - if err != nil { - return false, fmt.Errorf("error getting current path: %v", err) - } + path := GetMyPath() switch runtime.GOOS { case "windows": @@ -29,7 +24,7 @@ func CheckIfServiceIsActive(serv string) (bool, error) { return false, nil } - serviceStatus := strings.ToLower(strings.TrimSpace(string(output))) + serviceStatus := strings.ToLower(strings.TrimSpace(output)) if runtime.GOOS == "linux" { return serviceStatus == "active", nil } else if runtime.GOOS == "windows" { @@ -39,13 +34,8 @@ func CheckIfServiceIsActive(serv string) (bool, error) { return false, fmt.Errorf("unsupported operating system") } -// RestartService restarts a service func RestartService(serv string) error { - path, err := GetMyPath() - if err != nil { - return fmt.Errorf("error getting current path: %v", err) - } - + path := GetMyPath() isRunning, err := CheckIfServiceIsActive(serv) if err != nil { return fmt.Errorf("error checking if %s service is active: %v", serv, err) @@ -81,10 +71,7 @@ func RestartService(serv string) error { } func StopService(name string) error { - path, err := GetMyPath() - if err != nil { - return err - } + path := GetMyPath() switch runtime.GOOS { case "windows": err := Execute("sc", path, "stop", name) diff --git a/agent/self/utils/timestamp.go b/agent/self/utils/timestamp.go deleted file mode 100644 index e33aa0f2a..000000000 --- a/agent/self/utils/timestamp.go +++ /dev/null @@ -1,8 +0,0 @@ -package utils - -import "time" - -func GetCurrentTime() string { - t := time.Now() - return t.Format("20060102150405") -} diff --git a/agent/serv/clean-old.go b/agent/serv/clean-old.go new file mode 100644 index 000000000..489edd9b1 --- /dev/null +++ b/agent/serv/clean-old.go @@ -0,0 +1,65 @@ +package serv + +import ( + "fmt" + "os" + + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/utils" +) + +func CleanOldServices(cnf *config.Config) { + oldVersion := false + + isUpdaterINstalled, err := utils.CheckIfServiceIsInstalled("UTMStackUpdater") + if err != nil { + utils.Logger.ErrorF("Error checking if service is installed: %v", err) + } + + if isUpdaterINstalled { + oldVersion = true + err = utils.StopService("UTMStackUpdater") + if err != nil { + utils.Logger.ErrorF("Error stopping service: %v", err) + } + + err = utils.UninstallService("UTMStackUpdater") + if err != nil { + utils.Logger.ErrorF("Error uninstalling service: %v", err) + } + } + + isRedlineInstalled, err := utils.CheckIfServiceIsInstalled("UTMStackRedline") + if err != nil { + utils.Logger.ErrorF("Error checking if service is installed: %v", err) + } + + if isRedlineInstalled { + oldVersion = true + err = utils.StopService("UTMStackRedline") + if err != nil { + utils.Logger.ErrorF("Error stopping service: %v", err) + } + + err = utils.UninstallService("UTMStackRedline") + if err != nil { + utils.Logger.ErrorF("Error uninstalling service: %v", err) + } + } + + if oldVersion { + headers := map[string]string{ + "key": cnf.AgentKey, + "id": fmt.Sprintf("%v", cnf.AgentID), + "type": "agent", + } + + if err := utils.DownloadFile(fmt.Sprintf(config.DependUrl, cnf.Server, config.DependenciesPort, fmt.Sprintf(config.UpdaterSelf, "")), headers, fmt.Sprintf(config.UpdaterSelf, "_new"), utils.GetMyPath(), cnf.SkipCertValidation); err != nil { + utils.Logger.ErrorF("error downloading updater: %v", err) + return + } + + os.Remove(fmt.Sprintf(config.UpdaterSelf, "")) + os.Rename(fmt.Sprintf(config.UpdaterSelf, "_new"), fmt.Sprintf(config.UpdaterSelf, "")) + } +} diff --git a/agent/agent/serv/config.go b/agent/serv/config.go similarity index 91% rename from agent/agent/serv/config.go rename to agent/serv/config.go index f4e55ef55..90f9c683c 100644 --- a/agent/agent/serv/config.go +++ b/agent/serv/config.go @@ -10,6 +10,7 @@ func GetConfigServ() *service.Config { Name: "UTMStackAgent", DisplayName: "UTMStack Agent", Description: "UTMStack Agent Service", + Arguments: []string{"run"}, } return svcConfig diff --git a/agent/agent/serv/install.go b/agent/serv/install.go similarity index 50% rename from agent/agent/serv/install.go rename to agent/serv/install.go index 79bba16eb..06ab38a06 100644 --- a/agent/agent/serv/install.go +++ b/agent/serv/install.go @@ -1,25 +1,29 @@ package serv import ( + "fmt" + "os" + "github.com/kardianos/service" - "github.com/threatwinds/logger" ) -func InstallService(h *logger.Logger) { +func InstallService() { svcConfig := GetConfigServ() prg := new(program) newService, err := service.New(prg, svcConfig) if err != nil { - h.Fatal("error creating new service: %v", err) + fmt.Println("\nError creating new service: ", err) + os.Exit(1) } err = newService.Install() if err != nil { - h.Fatal("error installing new service: %v", err) + fmt.Println("\nError installing new service: ", err) + os.Exit(1) } - // Start the service after installing it err = newService.Start() if err != nil { - h.Fatal("error starting new service: %v", err) + fmt.Println("\nError starting new service: ", err) + os.Exit(1) } } diff --git a/agent/serv/run.go b/agent/serv/run.go new file mode 100644 index 000000000..d7d864905 --- /dev/null +++ b/agent/serv/run.go @@ -0,0 +1,19 @@ +package serv + +import ( + "github.com/kardianos/service" + "github.com/utmstack/UTMStack/agent/utils" +) + +func RunService() { + svcConfig := GetConfigServ() + p := new(program) + newService, err := service.New(p, svcConfig) + if err != nil { + utils.Logger.Fatal("error creating new service: %v", err) + } + err = newService.Run() + if err != nil { + utils.Logger.Fatal("error running new service: %v", err) + } +} diff --git a/agent/serv/service.go b/agent/serv/service.go new file mode 100644 index 000000000..8206cb220 --- /dev/null +++ b/agent/serv/service.go @@ -0,0 +1,62 @@ +package serv + +import ( + "context" + "os" + "os/signal" + "strconv" + "syscall" + + "github.com/kardianos/service" + pb "github.com/utmstack/UTMStack/agent/agent" + "github.com/utmstack/UTMStack/agent/collectors" + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/logservice" + "github.com/utmstack/UTMStack/agent/modules" + "github.com/utmstack/UTMStack/agent/updates" + "github.com/utmstack/UTMStack/agent/utils" + "google.golang.org/grpc/metadata" +) + +type program struct{} + +func (p *program) Start(s service.Service) error { + go p.run() + return nil +} + +func (p *program) Stop(s service.Service) error { + return nil +} + +func (p *program) run() { + utils.InitLogger(config.ServiceLogFile) + cnf, err := config.GetCurrentConfig() + if err != nil { + utils.Logger.Fatal("error getting config: %v", err) + } + + CleanOldServices(cnf) + + ctx, cancel := context.WithCancel(context.Background()) + defer cancel() + ctx = metadata.AppendToOutgoingContext(ctx, "key", cnf.AgentKey) + ctx = metadata.AppendToOutgoingContext(ctx, "id", strconv.Itoa(int(cnf.AgentID))) + ctx = metadata.AppendToOutgoingContext(ctx, "type", "agent") + + go pb.IncidentResponseStream(cnf, ctx) + go pb.StartPing(cnf, ctx) + + logProcessor := logservice.GetLogProcessor() + go logProcessor.ProcessLogs(cnf, ctx) + + go pb.UpdateAgent(cnf, ctx) + go modules.StartModules() + collectors.LogsReader() + + go updates.UpdateDependencies(cnf) + + signals := make(chan os.Signal, 1) + signal.Notify(signals, syscall.SIGINT, syscall.SIGTERM) + <-signals +} diff --git a/agent/serv/uninstall.go b/agent/serv/uninstall.go new file mode 100644 index 000000000..644bc713a --- /dev/null +++ b/agent/serv/uninstall.go @@ -0,0 +1,16 @@ +package serv + +import ( + "github.com/utmstack/UTMStack/agent/utils" +) + +func UninstallService() { + err := utils.StopService("UTMStackAgent") + if err != nil { + utils.Logger.Fatal("error stopping UTMStackAgent: %v", err) + } + err = utils.UninstallService("UTMStackAgent") + if err != nil { + utils.Logger.Fatal("error uninstalling UTMStackAgent: %v", err) + } +} diff --git a/agent/agent/templates/filebeat.yml b/agent/templates/filebeat.yml similarity index 100% rename from agent/agent/templates/filebeat.yml rename to agent/templates/filebeat.yml diff --git a/agent/agent/templates/winlogbeat.yml b/agent/templates/winlogbeat.yml similarity index 100% rename from agent/agent/templates/winlogbeat.yml rename to agent/templates/winlogbeat.yml diff --git a/agent/updater/README.md b/agent/updater/README.md deleted file mode 100644 index 253341f5b..000000000 --- a/agent/updater/README.md +++ /dev/null @@ -1,9 +0,0 @@ -# UTMStack Updater Service -UTMStack Updater Service is a crucial component of the UTMStack Agent. This service is responsible for monitoring updates for all UTMStack Agent services. If a new update is available, the UTMStack Updater Service will automatically download and install it. - -### Features -- Automatic Updates: The service regularly checks for updates to all UTMStack Agent services. If an update is available, it is downloaded and installed automatically, ensuring that your UTMStack Agent is always up-to-date with the latest features and security patches. - -- Logging: The service logs all its activities, making it easy to track its operations and troubleshoot any issues that may arise. - -- Service Management: The UTMStack Updater Service can be installed or uninstalled as needed. This provides flexibility in managing the services on your system. \ No newline at end of file diff --git a/agent/updater/configuration/config.go b/agent/updater/configuration/config.go deleted file mode 100644 index c3e47b1a1..000000000 --- a/agent/updater/configuration/config.go +++ /dev/null @@ -1,42 +0,0 @@ -package configuration - -import ( - "os" - "path/filepath" - - "github.com/utmstack/UTMStack/agent/updater/utils" -) - -type Config struct { - Server string `yaml:"server"` - AgentID uint `yaml:"agent-id"` - AgentKey string `yaml:"agent-key"` - SkipCertValidation bool `yaml:"insecure"` -} - -type Environment struct { - Branch string `yaml:"branch"` -} - -// ReadEnv reads the environment file -// If the file does not exist, it returns a default environment with release branch -// If the file exists, it returns the environment -func ReadEnv() (string, error) { - var env Environment - path, err := utils.GetMyPath() - if err != nil { - return "", err - } - - path = filepath.Join(path, "env.yml") - - if _, err = os.Stat(path); os.IsNotExist(err) { - return "release", nil - } else { - err = utils.ReadYAML(path, &env) - if err != nil { - return "", err - } - } - return env.Branch, nil -} diff --git a/agent/updater/configuration/const.go b/agent/updater/configuration/const.go deleted file mode 100644 index 2e89a5c31..000000000 --- a/agent/updater/configuration/const.go +++ /dev/null @@ -1,70 +0,0 @@ -package configuration - -import ( - "path/filepath" - "runtime" - "time" - - "github.com/utmstack/UTMStack/agent/updater/utils" -) - -const ( - SERV_NAME = "UTMStackUpdater" - SERV_LOG = "utmstack_updater.log" - SERV_LOCK = "utmstack_updater.lock" - MASTERVERSIONENDPOINT = "/management/info" - Bucket = "https://cdn.utmstack.com/agent_updates/" - CHECK_EVERY = 5 * time.Minute -) - -type ServiceAttribt struct { - ServName string - ServBin string - ServLock string -} - -// GetServAttr returns a map of ServiceAttribt -func GetServAttr() map[string]ServiceAttribt { - serAttr := map[string]ServiceAttribt{ - "agent": {ServName: "UTMStackAgent", ServBin: "utmstack_agent_service", ServLock: "utmstack_agent.lock"}, - "updater": {ServName: "UTMStackUpdater", ServBin: "utmstack_updater_self", ServLock: "utmstack_updater.lock"}, - "redline": {ServName: "UTMStackRedline", ServBin: "utmstack_redline_service", ServLock: "utmstack_redline.lock"}, - } - - switch runtime.GOOS { - case "windows": - for code, att := range serAttr { - att.ServBin += ".exe" - serAttr[code] = att - } - } - - return serAttr -} - -// GetAgentBin returns the agent binary name -func GetAgentBin() string { - bin := "utmstack_agent_service" - if runtime.GOOS == "windows" { - bin = bin + ".exe" - } - return bin -} - -// GetCertPath returns the path to the certificate -func GetCertPath() string { - path, _ := utils.GetMyPath() - return filepath.Join(path, "certs", "utm.crt") -} - -// GetKeyPath returns the path to the key -func GetKeyPath() string { - path, _ := utils.GetMyPath() - return filepath.Join(path, "certs", "utm.key") -} - -// GetCaPath returns the path to the CA -func GetCaPath() string { - path, _ := utils.GetMyPath() - return filepath.Join(path, "certs", "ca.crt") -} diff --git a/agent/updater/go.mod b/agent/updater/go.mod deleted file mode 100644 index 71f2464b2..000000000 --- a/agent/updater/go.mod +++ /dev/null @@ -1,43 +0,0 @@ -module github.com/utmstack/UTMStack/agent/updater - -go 1.22.4 - -toolchain go1.23.4 - -require ( - github.com/kardianos/service v1.2.2 - github.com/threatwinds/logger v1.1.12 - gopkg.in/yaml.v2 v2.4.0 -) - -require ( - github.com/bytedance/sonic v1.12.1 // indirect - github.com/bytedance/sonic/loader v0.2.0 // indirect - github.com/cloudwego/base64x v0.1.4 // indirect - github.com/cloudwego/iasm v0.2.0 // indirect - github.com/gabriel-vasile/mimetype v1.4.5 // indirect - github.com/gin-contrib/sse v0.1.0 // indirect - github.com/gin-gonic/gin v1.10.0 // indirect - github.com/go-playground/locales v0.14.1 // indirect - github.com/go-playground/universal-translator v0.18.1 // indirect - github.com/go-playground/validator/v10 v10.22.0 // indirect - github.com/goccy/go-json v0.10.3 // indirect - github.com/google/uuid v1.6.0 // indirect - github.com/json-iterator/go v1.1.12 // indirect - github.com/klauspost/cpuid/v2 v2.2.8 // indirect - github.com/leodido/go-urn v1.4.0 // indirect - github.com/mattn/go-isatty v0.0.20 // indirect - github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect - github.com/modern-go/reflect2 v1.0.2 // indirect - github.com/pelletier/go-toml/v2 v2.2.2 // indirect - github.com/twitchyliquid64/golang-asm v0.15.1 // indirect - github.com/ugorji/go/codec v1.2.12 // indirect - golang.org/x/arch v0.9.0 // indirect - golang.org/x/crypto v0.26.0 // indirect - golang.org/x/net v0.28.0 // indirect - golang.org/x/sys v0.24.0 // indirect - golang.org/x/text v0.17.0 // indirect - google.golang.org/protobuf v1.34.2 // indirect - gopkg.in/natefinch/lumberjack.v2 v2.2.1 // indirect - gopkg.in/yaml.v3 v3.0.1 // indirect -) diff --git a/agent/updater/go.sum b/agent/updater/go.sum deleted file mode 100644 index c0e35a1ff..000000000 --- a/agent/updater/go.sum +++ /dev/null @@ -1,99 +0,0 @@ -github.com/bytedance/sonic v1.12.1 h1:jWl5Qz1fy7X1ioY74WqO0KjAMtAGQs4sYnjiEBiyX24= -github.com/bytedance/sonic v1.12.1/go.mod h1:B8Gt/XvtZ3Fqj+iSKMypzymZxw/FVwgIGKzMzT9r/rk= -github.com/bytedance/sonic/loader v0.1.1/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= -github.com/bytedance/sonic/loader v0.2.0 h1:zNprn+lsIP06C/IqCHs3gPQIvnvpKbbxyXQP1iU4kWM= -github.com/bytedance/sonic/loader v0.2.0/go.mod h1:ncP89zfokxS5LZrJxl5z0UJcsk4M4yY2JpfqGeCtNLU= -github.com/cloudwego/base64x v0.1.4 h1:jwCgWpFanWmN8xoIUHa2rtzmkd5J2plF/dnLS6Xd/0Y= -github.com/cloudwego/base64x v0.1.4/go.mod h1:0zlkT4Wn5C6NdauXdJRhSKRlJvmclQ1hhJgA0rcu/8w= -github.com/cloudwego/iasm v0.2.0 h1:1KNIy1I1H9hNNFEEH3DVnI4UujN+1zjpuk6gwHLTssg= -github.com/cloudwego/iasm v0.2.0/go.mod h1:8rXZaNYT2n95jn+zTI1sDr+IgcD2GVs0nlbbQPiEFhY= -github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c= -github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38= -github.com/gabriel-vasile/mimetype v1.4.5 h1:J7wGKdGu33ocBOhGy0z653k/lFKLFDPJMG8Gql0kxn4= -github.com/gabriel-vasile/mimetype v1.4.5/go.mod h1:ibHel+/kbxn9x2407k1izTA1S81ku1z/DlgOW2QE0M4= -github.com/gin-contrib/sse v0.1.0 h1:Y/yl/+YNO8GZSjAhjMsSuLt29uWRFHdHYUb5lYOV9qE= -github.com/gin-contrib/sse v0.1.0/go.mod h1:RHrZQHXnP2xjPF+u1gW/2HnVO7nvIa9PG3Gm+fLHvGI= -github.com/gin-gonic/gin v1.10.0 h1:nTuyha1TYqgedzytsKYqna+DfLos46nTv2ygFy86HFU= -github.com/gin-gonic/gin v1.10.0/go.mod h1:4PMNQiOhvDRa013RKVbsiNwoyezlm2rm0uX/T7kzp5Y= -github.com/go-playground/assert/v2 v2.2.0 h1:JvknZsQTYeFEAhQwI4qEt9cyV5ONwRHC+lYKSsYSR8s= -github.com/go-playground/assert/v2 v2.2.0/go.mod h1:VDjEfimB/XKnb+ZQfWdccd7VUvScMdVu0Titje2rxJ4= -github.com/go-playground/locales v0.14.1 h1:EWaQ/wswjilfKLTECiXz7Rh+3BjFhfDFKv/oXslEjJA= -github.com/go-playground/locales v0.14.1/go.mod h1:hxrqLVvrK65+Rwrd5Fc6F2O76J/NuW9t0sjnWqG1slY= -github.com/go-playground/universal-translator v0.18.1 h1:Bcnm0ZwsGyWbCzImXv+pAJnYK9S473LQFuzCbDbfSFY= -github.com/go-playground/universal-translator v0.18.1/go.mod h1:xekY+UJKNuX9WP91TpwSH2VMlDf28Uj24BCp08ZFTUY= -github.com/go-playground/validator/v10 v10.22.0 h1:k6HsTZ0sTnROkhS//R0O+55JgM8C4Bx7ia+JlgcnOao= -github.com/go-playground/validator/v10 v10.22.0/go.mod h1:dbuPbCMFw/DrkbEynArYaCwl3amGuJotoKCe95atGMM= -github.com/goccy/go-json v0.10.3 h1:KZ5WoDbxAIgm2HNbYckL0se1fHD6rz5j4ywS6ebzDqA= -github.com/goccy/go-json v0.10.3/go.mod h1:oq7eo15ShAhp70Anwd5lgX2pLfOS3QCiwU/PULtXL6M= -github.com/google/go-cmp v0.5.5 h1:Khx7svrCpmxxtHBq5j2mp/xVjsi8hQMfNLvJFAlrGgU= -github.com/google/go-cmp v0.5.5/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= -github.com/google/gofuzz v1.0.0/go.mod h1:dBl0BpW6vV/+mYPU4Po3pmUjxk6FQPldtuIdl/M65Eg= -github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0= -github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo= -github.com/json-iterator/go v1.1.12 h1:PV8peI4a0ysnczrg+LtxykD8LfKY9ML6u2jnxaEnrnM= -github.com/json-iterator/go v1.1.12/go.mod h1:e30LSqwooZae/UwlEbR2852Gd8hjQvJoHmT4TnhNGBo= -github.com/kardianos/service v1.2.2 h1:ZvePhAHfvo0A7Mftk/tEzqEZ7Q4lgnR8sGz4xu1YX60= -github.com/kardianos/service v1.2.2/go.mod h1:CIMRFEJVL+0DS1a3Nx06NaMn4Dz63Ng6O7dl0qH0zVM= -github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg= -github.com/klauspost/cpuid/v2 v2.2.8 h1:+StwCXwm9PdpiEkPyzBXIy+M9KUb4ODm0Zarf1kS5BM= -github.com/klauspost/cpuid/v2 v2.2.8/go.mod h1:Lcz8mBdAVJIBVzewtcLocK12l3Y+JytZYpaMropDUws= -github.com/knz/go-libedit v1.10.1/go.mod h1:MZTVkCWyz0oBc7JOWP3wNAzd002ZbM/5hgShxwh4x8M= -github.com/leodido/go-urn v1.4.0 h1:WT9HwE9SGECu3lg4d/dIA+jxlljEa1/ffXKmRjqdmIQ= -github.com/leodido/go-urn v1.4.0/go.mod h1:bvxc+MVxLKB4z00jd1z+Dvzr47oO32F/QSNjSBOlFxI= -github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY= -github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y= -github.com/modern-go/concurrent v0.0.0-20180228061459-e0a39a4cb421/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd h1:TRLaZ9cD/w8PVh93nsPXa1VrQ6jlwL5oN8l14QlcNfg= -github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd/go.mod h1:6dJC0mAP4ikYIbvyc7fijjWJddQyLn8Ig3JB5CqoB9Q= -github.com/modern-go/reflect2 v1.0.2 h1:xBagoLtFs94CBntxluKeaWgTMpvLxC4ur3nMaC9Gz0M= -github.com/modern-go/reflect2 v1.0.2/go.mod h1:yWuevngMOJpCy52FWWMvUC8ws7m/LJsjYzDa0/r8luk= -github.com/pelletier/go-toml/v2 v2.2.2 h1:aYUidT7k73Pcl9nb2gScu7NSrKCSHIDE89b3+6Wq+LM= -github.com/pelletier/go-toml/v2 v2.2.2/go.mod h1:1t835xjRzz80PqgE6HHgN2JOsmgYu/h4qDAS4n929Rs= -github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM= -github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4= -github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= -github.com/stretchr/objx v0.4.0/go.mod h1:YvHI0jy2hoMjB+UWwv71VJQ9isScKT/TqJzVSSt89Yw= -github.com/stretchr/objx v0.5.0/go.mod h1:Yh+to48EsGEfYuaHDzXPcE3xhTkx73EhmCGUpEOglKo= -github.com/stretchr/objx v0.5.2/go.mod h1:FRsXN1f5AsAjCGJKqEizvkpNtU+EGNCLh3NxZ/8L+MA= -github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= -github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= -github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU= -github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o6fzry7u4= -github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= -github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= -github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= -github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= -github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= -github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= -github.com/ugorji/go/codec v1.2.12/go.mod h1:UNopzCgEMSXjBc6AOMqYvWC1ktqTAfzJZUZgYf6w6lg= -golang.org/x/arch v0.9.0 h1:ub9TgUInamJ8mrZIGlBG6/4TqWeMszd4N8lNorbrr6k= -golang.org/x/arch v0.9.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= -golang.org/x/crypto v0.26.0 h1:RrRspgV4mU+YwB4FYnuBoKsUapNIL5cohGAmSH3azsw= -golang.org/x/crypto v0.26.0/go.mod h1:GY7jblb9wI+FOo5y8/S2oY4zWP07AkOJ4+jxCqdqn54= -golang.org/x/net v0.28.0 h1:a9JDOJc5GMUJ0+UDqmLT86WiEy7iWyIhz8gz8E4e5hE= -golang.org/x/net v0.28.0/go.mod h1:yqtgsTWOOnlGLG9GFRrK3++bGOUEkNBoHZc8MEDWPNg= -golang.org/x/sys v0.0.0-20201015000850-e3ed0017c211/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= -golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.24.0 h1:Twjiwq9dn6R1fQcyiK+wQyHWfaz/BJB+YIpzU/Cv3Xg= -golang.org/x/sys v0.24.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/text v0.17.0 h1:XtiM5bkSOt+ewxlOE/aE/AKEHibwj/6gvWMl9Rsh0Qc= -golang.org/x/text v0.17.0/go.mod h1:BuEKDfySbSR4drPmRPG/7iBdf8hvFMuRexcpahXilzY= -golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= -golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= -google.golang.org/protobuf v1.34.2 h1:6xV6lTsCfpGD21XK49h7MhtcApnLqkfYgPcdHftf6hg= -google.golang.org/protobuf v1.34.2/go.mod h1:qYOHts0dSfpeUzUFpOMr/WGzszTmLH+DiWniOlNbLDw= -gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= -gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/natefinch/lumberjack.v2 v2.2.1 h1:bBRl1b0OH9s/DuPhuXpNl+VtCaJXFZ5/uEFST95x9zc= -gopkg.in/natefinch/lumberjack.v2 v2.2.1/go.mod h1:YD8tP3GAjkrDg1eZH7EGmyESg/lsYskCTPBJVb9jqSc= -gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY= -gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ= -gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA= -gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= -nullprogram.com/x/optparse v1.0.0/go.mod h1:KdyPE+Igbe0jQUrVfMqDMeJQIJZEuyV7pjYmp6pbG50= diff --git a/agent/updater/main.go b/agent/updater/main.go deleted file mode 100644 index 0a7ce9ea5..000000000 --- a/agent/updater/main.go +++ /dev/null @@ -1,55 +0,0 @@ -package main - -import ( - "fmt" - "log" - "os" - "path/filepath" - "time" - - "github.com/utmstack/UTMStack/agent/updater/configuration" - "github.com/utmstack/UTMStack/agent/updater/serv" - "github.com/utmstack/UTMStack/agent/updater/utils" -) - -func main() { - path, err := utils.GetMyPath() - if err != nil { - log.Fatalf("failed to get current path: %v", err) - } - - var h = utils.CreateLogger(filepath.Join(path, "logs", configuration.SERV_LOG)) - - if len(os.Args) > 1 { - mode := os.Args[1] - switch mode { - case "run": - serv.RunService(h) - case "install": - h.Info("Installing UTMStack Updater service...") - - if isInstalled, err := utils.CheckIfServiceIsInstalled(configuration.SERV_NAME); err != nil { - h.Fatal("error checking %s service: %v", configuration.SERV_NAME, err) - } else if isInstalled { - h.Fatal("%s is already installed", configuration.SERV_NAME) - } - - serv.InstallService(h) - h.Info("UTMStack Updater service installed correctly.") - time.Sleep(5 * time.Second) - os.Exit(0) - - case "uninstall": - h.Info("Uninstalling UTMStack Updater service...") - serv.UninstallService(h) - h.Info("UTMStack Updater service uninstalled correctly.") - time.Sleep(5 * time.Second) - os.Exit(0) - - default: - fmt.Println("unknown option") - } - } else { - serv.RunService(h) - } -} diff --git a/agent/updater/serv/config.go b/agent/updater/serv/config.go deleted file mode 100644 index 05c68ddf9..000000000 --- a/agent/updater/serv/config.go +++ /dev/null @@ -1,17 +0,0 @@ -package serv - -import ( - "github.com/kardianos/service" - "github.com/utmstack/UTMStack/agent/updater/configuration" -) - -// GetConfigServ creates and returns a pointer to a service configuration structure. -func GetConfigServ() *service.Config { - svcConfig := &service.Config{ - Name: configuration.SERV_NAME, - DisplayName: "UTMStack Updater", - Description: "UTMStack Updater Service", - } - - return svcConfig -} diff --git a/agent/updater/serv/install.go b/agent/updater/serv/install.go deleted file mode 100644 index 297aecdae..000000000 --- a/agent/updater/serv/install.go +++ /dev/null @@ -1,31 +0,0 @@ -package serv - -import ( - "fmt" - - "github.com/kardianos/service" - "github.com/threatwinds/logger" -) - -// InstallService installs the service in the system and starts it -func InstallService(utmLogger *logger.Logger) { - svcConfig := GetConfigServ() - prg := new(program) - newService, err := service.New(prg, svcConfig) - if err != nil { - fmt.Printf("error creating new service: %v", err) - utmLogger.Fatal("error creating new service: %v", err) - } - err = newService.Install() - if err != nil { - fmt.Printf("error installing new service: %v", err) - utmLogger.Fatal("error installing new service: %v", err) - } - - // Start the service after installing it - err = newService.Start() - if err != nil { - fmt.Printf("error starting new service: %v", err) - utmLogger.Fatal("error starting new service: %v", err) - } -} diff --git a/agent/updater/serv/run.go b/agent/updater/serv/run.go deleted file mode 100644 index 5581325d2..000000000 --- a/agent/updater/serv/run.go +++ /dev/null @@ -1,20 +0,0 @@ -package serv - -import ( - "github.com/kardianos/service" - "github.com/threatwinds/logger" -) - -// RunService runs the service in the system -func RunService(utmLogger *logger.Logger) { - svcConfig := GetConfigServ() - prg := new(program) - newService, err := service.New(prg, svcConfig) - if err != nil { - utmLogger.Fatal("error creating new service: %v", err) - } - err = newService.Run() - if err != nil { - utmLogger.Fatal("error running new service: %v", err) - } -} diff --git a/agent/updater/serv/service.go b/agent/updater/serv/service.go deleted file mode 100644 index 6f74b2e7a..000000000 --- a/agent/updater/serv/service.go +++ /dev/null @@ -1,63 +0,0 @@ -package serv - -import ( - "log" - "os" - "os/signal" - "path/filepath" - "syscall" - "time" - - "github.com/kardianos/service" - "github.com/utmstack/UTMStack/agent/updater/configuration" - "github.com/utmstack/UTMStack/agent/updater/updates" - "github.com/utmstack/UTMStack/agent/updater/utils" -) - -type program struct{} - -func (p *program) Start(s service.Service) error { - go p.run() - return nil -} - -func (p *program) Stop(s service.Service) error { - return nil -} - -func (p *program) run() { - // Get current path - path, err := utils.GetMyPath() - if err != nil { - log.Fatalf("Failed to get current path: %v", err) - } - - // Configuring log saving - var h = utils.CreateLogger(filepath.Join(path, "logs", configuration.SERV_LOG)) - - for { - isActive, err := utils.CheckIfServiceIsActive(configuration.GetServAttr()["agent"].ServName) - if err != nil { - time.Sleep(time.Second * 5) - h.ErrorF("error checking if %s service is active: %v", configuration.GetServAttr()["agent"].ServName, err) - continue - } else if !isActive { - time.Sleep(time.Second * 5) - continue - } - break - } - - var cnf configuration.Config - err = utils.ReadYAML(filepath.Join(path, "config.yml"), &cnf) - if err != nil { - h.Fatal("error reading config.yml: %v", err) - } - - go updates.UpdateServices(cnf, h) - - signals := make(chan os.Signal, 1) - signal.Notify(signals, syscall.SIGINT, syscall.SIGTERM) - <-signals - -} diff --git a/agent/updater/serv/uninstall.go b/agent/updater/serv/uninstall.go deleted file mode 100644 index c66b742a5..000000000 --- a/agent/updater/serv/uninstall.go +++ /dev/null @@ -1,20 +0,0 @@ -package serv - -import ( - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/updater/configuration" - "github.com/utmstack/UTMStack/agent/updater/utils" -) - -// UninstallService uninstalls the service in the system -func UninstallService(utmLogger *logger.Logger) { - // Uninstall service - err := utils.StopService(configuration.SERV_NAME) - if err != nil { - utmLogger.Fatal("error stopping %s: %v", configuration.SERV_NAME, err) - } - err = utils.UninstallService(configuration.SERV_NAME) - if err != nil { - utmLogger.Fatal("error uninstalling %s: %v", configuration.SERV_NAME, err) - } -} diff --git a/agent/updater/updates/schema.go b/agent/updater/updates/schema.go deleted file mode 100644 index a36f0d280..000000000 --- a/agent/updater/updates/schema.go +++ /dev/null @@ -1,29 +0,0 @@ -package updates - -import "encoding/json" - -type InfoResponse struct { - Display string `json:"display-ribbon-on-profiles"` - Git json.RawMessage `json:"git"` - Build Build `json:"build"` - Profiles []string `json:"activeProfiles"` -} - -type Build struct { - Artifact string `json:"artifact"` - Name string `json:"name"` - Time string `json:"time"` - Version string `json:"version"` - Group string `json:"group"` -} - -type DataVersions struct { - Versions []Version `json:"versions"` -} - -type Version struct { - MasterVersion string `json:"master_version"` - AgentVersion string `json:"agent_version"` - UpdaterVersion string `json:"updater_version"` - RedlineVersion string `json:"redline_version"` -} diff --git a/agent/updater/updates/service.go b/agent/updater/updates/service.go deleted file mode 100644 index 5c4953934..000000000 --- a/agent/updater/updates/service.go +++ /dev/null @@ -1,164 +0,0 @@ -package updates - -import ( - "fmt" - "path/filepath" - "runtime" - "sync" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/updater/configuration" - "github.com/utmstack/UTMStack/agent/updater/utils" -) - -type UTMServices struct { - MasterVersion string - CurrentVersions Version - LatestVersions Version - ServAttr map[string]configuration.ServiceAttribt -} - -func (u *UTMServices) UpdateCurrentMasterVersion(cnf configuration.Config) error { - masterVersion, err := getMasterVersion(cnf.Server, cnf.SkipCertValidation) - if err != nil { - return fmt.Errorf("error getting master version: %v", err) - } - u.MasterVersion = masterVersion - return nil -} - -func (u *UTMServices) UpdateCurrentVersions() error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } - - err = utils.ReadJson(filepath.Join(path, "versions.json"), &u.CurrentVersions) - if err != nil { - return fmt.Errorf("error reading current versions.json: %v", err) - } - - return nil -} - -func (u *UTMServices) UpdateLatestVersions(env string, utmLogger *logger.Logger) error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } - - err = utils.DownloadFile(configuration.Bucket+env+"/versions.json", filepath.Join(path, "versions.json"), utmLogger) - if err != nil { - return fmt.Errorf("error downloading latest versions.json: %v", err) - } - - newData := DataVersions{} - err = utils.ReadJson(filepath.Join(path, "versions.json"), &newData) - if err != nil { - return fmt.Errorf("error reading latest versions.json: %v", err) - } - - u.LatestVersions = getLatestVersion(newData, u.MasterVersion) - err = utils.WriteJSON(filepath.Join(path, "versions.json"), &u.LatestVersions) - if err != nil { - return fmt.Errorf("error writing versions.json: %v", err) - } - - return nil -} - -func (u *UTMServices) CheckUpdates(env string, utmLogger *logger.Logger) error { - path, err := utils.GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } - - if isVersionGreater(u.CurrentVersions.RedlineVersion, u.LatestVersions.RedlineVersion) { - err := u.UpdateService(path, env, "redline", u.LatestVersions.RedlineVersion, utmLogger) - if err != nil { - return fmt.Errorf("error updating UTMStackRedline service: %v", err) - } - utmLogger.Info("UTMStackRedline service updated correctly") - } - - if isVersionGreater(u.CurrentVersions.AgentVersion, u.LatestVersions.AgentVersion) { - err := u.UpdateService(path, env, "agent", u.LatestVersions.AgentVersion, utmLogger) - if err != nil { - return fmt.Errorf("error updating UTMStackAgent service: %v", err) - } - utmLogger.Info("UTMStackAgent service updated correctly") - } - - if isVersionGreater(u.CurrentVersions.UpdaterVersion, u.LatestVersions.UpdaterVersion) { - err := u.UpdateService(path, env, "updater", u.LatestVersions.UpdaterVersion, utmLogger) - if err != nil { - return fmt.Errorf("error updating UTMStackUpdater service: %v", err) - } - utmLogger.Info("UTMStackUpdater service updated correctly") - } - - return nil -} - -func (u *UTMServices) UpdateService(path string, env string, servCode string, newVers string, utmLogger *logger.Logger) error { - attr := u.ServAttr[servCode] - err := utils.CreatePathIfNotExist(filepath.Join(path, "locks")) - if err != nil { - return fmt.Errorf("error creating locks path: %v", err) - } - - err = utils.SetLock(filepath.Join(path, "locks", attr.ServLock)) - if err != nil { - return fmt.Errorf("error setting lock %s: %v", attr.ServLock, err) - } - - if servCode == "updater" { - utils.Execute(filepath.Join(path, attr.ServBin), path) - } else { - err = utils.StopService(attr.ServName) - if err != nil { - return fmt.Errorf("error stoping %s service: %v", attr.ServName, err) - } - - url := configuration.Bucket + env + "/" + servCode + "_service/v" + newVers + "/" + attr.ServBin + "?time=" + utils.GetCurrentTime() - err = utils.DownloadFile(url, filepath.Join(path, attr.ServBin), utmLogger) - if err != nil { - return fmt.Errorf("error downloading new %s: %v", attr.ServBin, err) - } - - if runtime.GOOS == "linux" { - if err = utils.Execute("chmod", path, "-R", "777", attr.ServBin); err != nil { - return fmt.Errorf("error executing chmod: %v", err) - } - } - - err = utils.RestartService(attr.ServName) - if err != nil { - return fmt.Errorf("error restarting %s service: %v", attr.ServName, err) - } - } - - err = utils.RemoveLock(filepath.Join(path, "locks", attr.ServLock)) - if err != nil { - return fmt.Errorf("error removing lock %s: %v", attr.ServLock, err) - } - - return nil -} - -var ( - utmServ UTMServices - utmServOnce sync.Once -) - -func GetUTMServicesInstance() UTMServices { - utmServOnce.Do(func() { - utmServ = UTMServices{ - MasterVersion: "", - CurrentVersions: Version{}, - LatestVersions: Version{}, - ServAttr: configuration.GetServAttr(), - } - }) - return utmServ -} diff --git a/agent/updater/updates/update.go b/agent/updater/updates/update.go deleted file mode 100644 index cfed20ba1..000000000 --- a/agent/updater/updates/update.go +++ /dev/null @@ -1,48 +0,0 @@ -package updates - -import ( - "time" - - "github.com/threatwinds/logger" - "github.com/utmstack/UTMStack/agent/updater/configuration" -) - -func UpdateServices(cnf configuration.Config, utmLogger *logger.Logger) { - utmServices := GetUTMServicesInstance() - - env, err := configuration.ReadEnv() - if err != nil { - utmLogger.Fatal("error reading environment configuration: %v", err) - } - - utmLogger.Info("enviroment: %v", env) - - for { - time.Sleep(configuration.CHECK_EVERY) - - err = utmServices.UpdateCurrentMasterVersion(cnf) - if err != nil { - utmLogger.ErrorF("error updating current master version: %v", err) - continue - } - - err = utmServices.UpdateCurrentVersions() - if err != nil { - utmLogger.ErrorF("error updating current versions: %v", err) - continue - } - - err = utmServices.UpdateLatestVersions(env, utmLogger) - if err != nil { - utmLogger.ErrorF("error updating latest versions: %v", err) - continue - } - - err = utmServices.CheckUpdates(env, utmLogger) - if err != nil { - utmLogger.ErrorF("error updating services: %v", err) - continue - } - - } -} diff --git a/agent/updater/updates/version.go b/agent/updater/updates/version.go deleted file mode 100644 index 5f1f6c078..000000000 --- a/agent/updater/updates/version.go +++ /dev/null @@ -1,85 +0,0 @@ -package updates - -import ( - "crypto/tls" - "fmt" - "net/http" - "strconv" - "strings" - - "github.com/utmstack/UTMStack/agent/updater/configuration" - "github.com/utmstack/UTMStack/agent/updater/utils" -) - -// getLatestVersion returns the latest version of the service -func getLatestVersion(versions DataVersions, masterVersions string) Version { - for _, vers := range versions.Versions { - if vers.MasterVersion == masterVersions { - return vers - } - } - return Version{} -} - -// getMasterVersion returns the master version of the service -func getMasterVersion(ip string, skip bool) (string, error) { - config := &tls.Config{InsecureSkipVerify: skip} - if !skip { - var err error - config, err = utils.LoadTLSCredentials(configuration.GetCertPath()) - if err != nil { - return "", fmt.Errorf("error loading tls credentials: %v", err) - } - } - resp, status, err := utils.DoReq[InfoResponse]("https://"+ip+configuration.MASTERVERSIONENDPOINT, nil, http.MethodGet, map[string]string{}, config) - if err != nil { - return "", err - } else if status != http.StatusOK { - return "", fmt.Errorf("status code %d: %v", status, resp) - } - return resp.Build.Version, nil -} - -// isVersionGreater returns true if newVersion is greater than oldVersion -func isVersionGreater(oldVersion, newVersion string) bool { - oldParts := strings.Split(oldVersion, ".") - newParts := strings.Split(newVersion, ".") - - for i, oldPart := range oldParts { - nOld, _ := strconv.Atoi(oldPart) - if i < len(newParts) { - nNew, _ := strconv.Atoi(newParts[i]) - if nNew > nOld { - return true - } else if nNew < nOld { - return false - } - } - } - return false -} - -/* -func isNewOrEqualVersion(oldVersion, newVersion string) bool { - oldParts := strings.Split(oldVersion, ".") - newParts := strings.Split(newVersion, ".") - - minLength := len(oldParts) - if len(newParts) < minLength { - minLength = len(newParts) - } - - for i := 0; i < minLength; i++ { - nOld, _ := strconv.Atoi(oldParts[i]) - nNew, _ := strconv.Atoi(newParts[i]) - - if nNew > nOld { - return true - } else if nNew < nOld { - return false - } - } - - return len(newParts) >= len(oldParts) -} -*/ diff --git a/agent/updater/utils/cmd.go b/agent/updater/utils/cmd.go deleted file mode 100644 index 686c93f95..000000000 --- a/agent/updater/utils/cmd.go +++ /dev/null @@ -1,50 +0,0 @@ -package utils - -import ( - "errors" - "os/exec" - "unicode/utf8" -) - -// ExecuteWithResult executes a command and returns the output -func ExecuteWithResult(c string, dir string, arg ...string) (string, bool) { - cmd := exec.Command(c, arg...) - - cmd.Dir = dir - if errors.Is(cmd.Err, exec.ErrDot) { - cmd.Err = nil - } - - out, err := cmd.Output() - if err != nil { - return string(out[:]) + err.Error(), true - } - - validUtf8Out := cleanString(string(out[:])) - - return validUtf8Out, false -} - -// Execute executes a command without returning the output -func Execute(c string, dir string, arg ...string) error { - cmd := exec.Command(c, arg...) - cmd.Dir = dir - - return cmd.Run() -} - -// cleanString cleans a string from invalid utf8 characters -func cleanString(s string) string { - v := make([]rune, 0, len(s)) - for i, r := range s { - if r == utf8.RuneError { - _, size := utf8.DecodeRuneInString(s[i:]) - if size == 1 { - v = append(v, '?') - continue - } - } - v = append(v, r) - } - return string(v) -} diff --git a/agent/updater/utils/delay.go b/agent/updater/utils/delay.go deleted file mode 100644 index 61193d39b..000000000 --- a/agent/updater/utils/delay.go +++ /dev/null @@ -1,12 +0,0 @@ -package utils - -import "time" - -// IncrementReconnectDelay increments the delay for reconnecting to the server -func IncrementReconnectDelay(delay time.Duration, maxReconnectDelay time.Duration) time.Duration { - delay *= 2 - if delay > maxReconnectDelay { - delay = maxReconnectDelay - } - return delay -} diff --git a/agent/updater/utils/download.go b/agent/updater/utils/download.go deleted file mode 100644 index d313e8054..000000000 --- a/agent/updater/utils/download.go +++ /dev/null @@ -1,43 +0,0 @@ -package utils - -import ( - "io" - "net/http" - "os" - "time" - - "github.com/threatwinds/logger" -) - -const ( - reconnectDelay = 5 * time.Minute -) - -// DownloadFile downloads a file from a URL and saves it to disk. Returns an error on failure. -func DownloadFile(url string, fileName string, utmLogger *logger.Logger) error { - var resp *http.Response - var err error - - for { - resp, err = http.Get(url) - if err != nil || resp.StatusCode != http.StatusOK { - if resp != nil { - resp.Body.Close() - } - utmLogger.ErrorF("error downloading file from %s: %v", url, err) - time.Sleep(reconnectDelay) - continue - } - break - } - defer resp.Body.Close() - - out, err := os.Create(fileName) - if err != nil { - return err - } - defer out.Close() - - _, err = io.Copy(out, resp.Body) - return err -} diff --git a/agent/updater/utils/files.go b/agent/updater/utils/files.go deleted file mode 100644 index 1006b2c0f..000000000 --- a/agent/updater/utils/files.go +++ /dev/null @@ -1,99 +0,0 @@ -package utils - -import ( - "encoding/json" - "fmt" - "os" - "path/filepath" - - "gopkg.in/yaml.v2" -) - -// GetMyPath returns the directory path where the currently running executable is located. -// Returns a string representing the directory path, and an error if any error occurs during the process. -func GetMyPath() (string, error) { - ex, err := os.Executable() - if err != nil { - return "", err - } - exPath := filepath.Dir(ex) - return exPath, nil -} - -// ReadYAML reads the YAML data from the specified file URL and deserializes it into the provided result interface{}. -// Returns an error if any error occurs during the process. -func ReadYAML(path string, result interface{}) error { - file, err := os.Open(path) - if err != nil { - return err - } - defer file.Close() - d := yaml.NewDecoder(file) - if err := d.Decode(result); err != nil { - return err - } - return nil -} - -// ReadJson reads the json data from the specified file URL and unmarshal it into the provided result interface{}. -// Returns an error if any error occurs during the process. -func ReadJson(fileName string, data interface{}) error { - content, err := os.ReadFile(fileName) - if err != nil { - return err - } - err = json.Unmarshal(content, data) - if err != nil { - return err - } - return nil -} - -// WriteJSON writes the provided data interface{} to the specified file URL in JSON format. -func WriteJSON(path string, data interface{}) error { - jsonData, err := json.MarshalIndent(data, "", " ") - if err != nil { - return err - } - - err = writeToFile(path, string(jsonData[:])) - if err != nil { - return err - } - - return nil -} - -// CreatePathIfNotExist creates a specific path if not exist -func CreatePathIfNotExist(path string) error { - if _, err := os.Stat(path); os.IsNotExist(err) { - if err := os.Mkdir(path, 0755); err != nil { - return fmt.Errorf("error creating path: %v", err) - } - } else if err != nil { - return fmt.Errorf("error checking path: %v", err) - } - return nil -} - -// CheckIfPathExist checks if a specific path exists -func CheckIfPathExist(path string) bool { - if _, err := os.Stat(path); os.IsNotExist(err) { - return false - } - return true -} - -// writeToFile writes the provided body string to the specified file URL. -func writeToFile(fileName string, body string) error { - file, err := os.OpenFile(fileName, os.O_CREATE|os.O_RDWR|os.O_TRUNC, os.ModePerm) - - if err != nil { - return err - } - - defer file.Close() - - _, err = file.WriteString(body) - return err -} diff --git a/agent/updater/utils/lock.go b/agent/updater/utils/lock.go deleted file mode 100644 index 261ee0415..000000000 --- a/agent/updater/utils/lock.go +++ /dev/null @@ -1,31 +0,0 @@ -package utils - -import ( - "fmt" - "os" -) - -// SetLock creates a lock file -func SetLock(lockdir string) error { - if !CheckIfPathExist(lockdir) { - file, err := os.OpenFile(lockdir, os.O_CREATE|os.O_RDWR|os.O_TRUNC, os.ModePerm) - if err != nil { - return err - } - defer file.Close() - } - return nil -} - -// RemoveLock removes a lock file -func RemoveLock(lockdir string) error { - if CheckIfPathExist(lockdir) { - err := os.Remove(lockdir) - if err != nil { - return err - } - } else { - return fmt.Errorf("lock file %s not exists", lockdir) - } - return nil -} diff --git a/agent/updater/utils/logger.go b/agent/updater/utils/logger.go deleted file mode 100644 index 213f64a69..000000000 --- a/agent/updater/utils/logger.go +++ /dev/null @@ -1,22 +0,0 @@ -package utils - -import ( - "sync" - - "github.com/threatwinds/logger" -) - -var ( - agentLogger *logger.Logger - loggerOnceInstance sync.Once -) - -// CreateLogger returns a single instance of a Logger configured to save logs to a rotating file. -func CreateLogger(filename string) *logger.Logger { - loggerOnceInstance.Do(func() { - agentLogger = logger.NewLogger( - &logger.Config{Format: "text", Level: 100, Output: filename, Retries: 3, Wait: 5}, - ) - }) - return agentLogger -} diff --git a/agent/updater/utils/req.go b/agent/updater/utils/req.go deleted file mode 100644 index 5e8a639af..000000000 --- a/agent/updater/utils/req.go +++ /dev/null @@ -1,51 +0,0 @@ -package utils - -import ( - "bytes" - "crypto/tls" - "encoding/json" - "io" - "net/http" -) - -// DoReq makes a request to the specified URL with the specified data, method and headers. -func DoReq[response any](url string, data []byte, method string, headers map[string]string, config *tls.Config) (response, int, error) { - req, err := http.NewRequest(method, url, bytes.NewBuffer(data)) - if err != nil { - return *new(response), http.StatusInternalServerError, err - } - - for k, v := range headers { - req.Header.Add(k, v) - } - - transp := &http.Transport{ - TLSClientConfig: config, - } - - client := &http.Client{Transport: transp} - - resp, err := client.Do(req) - if err != nil { - return *new(response), http.StatusInternalServerError, err - } - defer resp.Body.Close() - - body, err := io.ReadAll(resp.Body) - if err != nil { - return *new(response), http.StatusInternalServerError, err - } - - var result response - - err = json.Unmarshal(body, &result) - if err != nil { - return *new(response), http.StatusInternalServerError, err - } - - if resp.StatusCode != http.StatusAccepted && resp.StatusCode != http.StatusOK { - return *new(response), http.StatusInternalServerError, err - } - - return result, resp.StatusCode, nil -} diff --git a/agent/updater/utils/services.go b/agent/updater/utils/services.go deleted file mode 100644 index 96d9b18f4..000000000 --- a/agent/updater/utils/services.go +++ /dev/null @@ -1,146 +0,0 @@ -package utils - -import ( - "fmt" - "os/exec" - "runtime" - "strings" -) - -// CheckIfServiceIsActive checks if a service is active or running -func CheckIfServiceIsActive(serv string) (bool, error) { - var errB bool - var output string - - path, err := GetMyPath() - if err != nil { - return false, fmt.Errorf("error getting current path: %v", err) - } - - switch runtime.GOOS { - case "windows": - output, errB = ExecuteWithResult("sc", path, "query", serv) - case "linux": - output, errB = ExecuteWithResult("systemctl", path, "is-active", serv) - default: - return false, fmt.Errorf("unknown operating system") - } - - if errB { - return false, nil - } - - serviceStatus := strings.ToLower(strings.TrimSpace(string(output))) - if runtime.GOOS == "linux" { - return serviceStatus == "active", nil - } else if runtime.GOOS == "windows" { - return strings.Contains(serviceStatus, "running"), nil - } - - return false, fmt.Errorf("unsupported operating system") -} - -// RestartService restarts a service -func RestartService(serv string) error { - path, err := GetMyPath() - if err != nil { - return fmt.Errorf("error getting current path: %v", err) - } - - isRunning, err := CheckIfServiceIsActive(serv) - if err != nil { - return fmt.Errorf("error checking if %s service is active: %v", serv, err) - } - - switch runtime.GOOS { - case "windows": - if isRunning { - err := Execute("sc", path, "stop", serv) - if err != nil { - return fmt.Errorf("error stopping service: %v", err) - } - } - err := Execute("sc", path, "start", serv) - if err != nil { - return fmt.Errorf("error starting service: %v", err) - } - - case "linux": - if isRunning { - err := Execute("systemctl", path, "restart", serv) - if err != nil { - return fmt.Errorf("error restarting service: %v", err) - } - } else { - err := Execute("systemctl", path, "start", serv) - if err != nil { - return fmt.Errorf("error starting service: %v", err) - } - } - } - return nil -} - -// StopService stops a service -func StopService(name string) error { - path, err := GetMyPath() - if err != nil { - return err - } - switch runtime.GOOS { - case "windows": - err := Execute("sc", path, "stop", name) - if err != nil { - return fmt.Errorf("error stoping service: %v", err) - } - case "linux": - err := Execute("systemctl", path, "stop", name) - if err != nil { - return fmt.Errorf("error stoping service: %v", err) - } - } - return nil -} - -// UninstallService uninstalls a service -func UninstallService(name string) error { - path, err := GetMyPath() - if err != nil { - return err - } - switch runtime.GOOS { - case "windows": - err := Execute("sc", path, "delete", name) - if err != nil { - return fmt.Errorf("error uninstalling service: %v", err) - } - case "linux": - err := Execute("systemctl", path, "disable", name) - if err != nil { - return fmt.Errorf("error uninstalling service: %v", err) - } - err = Execute("rm", "/etc/systemd/system/", "/etc/systemd/system/"+name+".service") - if err != nil { - return fmt.Errorf("error uninstalling service: %v", err) - } - } - return nil -} - -// CheckIfServiceIsInstalled checks if a service is installed -func CheckIfServiceIsInstalled(serv string) (bool, error) { - var cmd *exec.Cmd - switch runtime.GOOS { - case "windows": - cmd = exec.Command("sc", "query", serv) - case "linux": - cmd = exec.Command("systemctl", "status", serv) - default: - return false, fmt.Errorf("operative system unknown") - } - - if err := cmd.Run(); err != nil { - return false, nil - } - return true, nil -} diff --git a/agent/updater/utils/timestamp.go b/agent/updater/utils/timestamp.go deleted file mode 100644 index 7fbb24f2e..000000000 --- a/agent/updater/utils/timestamp.go +++ /dev/null @@ -1,9 +0,0 @@ -package utils - -import "time" - -// GetCurrentTime returns the current time in the format YYYYMMDDHHMMSS -func GetCurrentTime() string { - t := time.Now() - return t.Format("20060102150405") -} diff --git a/agent/updater/utils/tls.go b/agent/updater/utils/tls.go deleted file mode 100644 index d0a1bb693..000000000 --- a/agent/updater/utils/tls.go +++ /dev/null @@ -1,28 +0,0 @@ -package utils - -import ( - "crypto/tls" - "crypto/x509" - "fmt" - "os" -) - -// LoadTLSCredentials loads the TLS credentials from the specified certificate file. -func LoadTLSCredentials(crtName string) (*tls.Config, error) { - // Load the server's certificate - serverCert, err := os.ReadFile(crtName) - if err != nil { - return nil, err - } - - certPool := x509.NewCertPool() - if !certPool.AppendCertsFromPEM(serverCert) { - return nil, fmt.Errorf("failed to add server certificate to the certificate pool") - } - - config := &tls.Config{ - RootCAs: certPool, - } - - return config, nil -} diff --git a/agent/updates/dependencies.go b/agent/updates/dependencies.go new file mode 100644 index 000000000..a740f3551 --- /dev/null +++ b/agent/updates/dependencies.go @@ -0,0 +1,60 @@ +package updates + +import ( + "fmt" + "os" + "path/filepath" + "runtime" + "strings" + + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/utils" +) + +func DownloadFirstDependencies(address string, authKey string, insecure bool) error { + headers := map[string]string{"connection-key": authKey} + + if err := utils.DownloadFile(fmt.Sprintf(config.DependUrl, address, config.DependenciesPort, "version.json"), headers, "version.json", utils.GetMyPath(), insecure); err != nil { + return fmt.Errorf("error downloading version.json : %v", err) + } + + dependFiles := config.DependFiles + for _, file := range dependFiles { + if err := utils.DownloadFile(fmt.Sprintf(config.DependUrl, address, config.DependenciesPort, file), headers, file, utils.GetMyPath(), insecure); err != nil { + return fmt.Errorf("error downloading file %s: %v", file, err) + } + } + + if err := handleDependenciesPostDownload(dependFiles); err != nil { + return err + } + + return nil + +} + +func handleDependenciesPostDownload(dependencies []string) error { + for _, file := range dependencies { + if strings.HasSuffix(file, ".zip") { + if err := utils.Unzip(filepath.Join(utils.GetMyPath(), file), utils.GetMyPath()); err != nil { + return fmt.Errorf("error unzipping dependencies: %v", err) + } + + if runtime.GOOS == "linux" { + if err := utils.Execute("chmod", utils.GetMyPath(), "-R", "777", fmt.Sprintf(config.UpdaterSelf, "")); err != nil { + return fmt.Errorf("error executing chmod on %s: %v", fmt.Sprintf(config.UpdaterSelf, ""), err) + } + } + + if err := os.Remove(filepath.Join(utils.GetMyPath(), file)); err != nil { + return fmt.Errorf("error removing file %s: %v", file, err) + } + } else if runtime.GOOS == "linux" { + if err := utils.Execute("chmod", utils.GetMyPath(), "-R", "777", file); err != nil { + return fmt.Errorf("error executing chmod on %s: %v", file, err) + } + } + } + + return nil +} diff --git a/agent/updates/update.go b/agent/updates/update.go new file mode 100644 index 000000000..4b4312c8c --- /dev/null +++ b/agent/updates/update.go @@ -0,0 +1,73 @@ +package updates + +import ( + "fmt" + "os" + "path/filepath" + "runtime" + "time" + + "github.com/utmstack/UTMStack/agent/config" + "github.com/utmstack/UTMStack/agent/models" + "github.com/utmstack/UTMStack/agent/utils" +) + +const ( + checkEvery = 5 * time.Minute +) + +var currentVersion = models.Version{} + +func UpdateDependencies(cnf *config.Config) { + if utils.CheckIfPathExist(config.VersionPath) { + err := utils.ReadJson(config.VersionPath, ¤tVersion) + if err != nil { + utils.Logger.Fatal("error reading version file: %v", err) + } + } + + for { + time.Sleep(checkEvery) + + headers := map[string]string{ + "key": cnf.AgentKey, + "id": fmt.Sprintf("%v", cnf.AgentID), + "type": "agent", + } + + if err := utils.DownloadFile(fmt.Sprintf(config.DependUrl, cnf.Server, config.DependenciesPort, "version.json"), headers, "version_new.json", utils.GetMyPath(), cnf.SkipCertValidation); err != nil { + utils.Logger.ErrorF("error downloading version.json: %v", err) + continue + } + newVersion := models.Version{} + err := utils.ReadJson(filepath.Join(utils.GetMyPath(), "version_new.json"), &newVersion) + if err != nil { + utils.Logger.ErrorF("error reading version file: %v", err) + continue + } + + if newVersion.Version != currentVersion.Version { + utils.Logger.Info("New version of agent found: %s", newVersion.Version) + if err := utils.DownloadFile(fmt.Sprintf(config.DependUrl, cnf.Server, fmt.Sprintf(config.ServiceFile, "")), headers, fmt.Sprintf(config.ServiceFile, "_new"), utils.GetMyPath(), cnf.SkipCertValidation); err != nil { + utils.Logger.ErrorF("error downloading agent: %v", err) + continue + } + + currentVersion = newVersion + err = utils.WriteJSON(config.VersionPath, ¤tVersion) + if err != nil { + utils.Logger.ErrorF("error writing version file: %v", err) + continue + } + os.Remove(filepath.Join(utils.GetMyPath(), "version_new.json")) + + if runtime.GOOS == "linux" { + if err = utils.Execute("chmod", utils.GetMyPath(), "-R", "777", filepath.Join(utils.GetMyPath(), fmt.Sprintf(config.ServiceFile, "_new"))); err != nil { + utils.Logger.ErrorF("error executing chmod: %v", err) + } + } + + utils.Execute(fmt.Sprintf(config.UpdaterSelf, ""), utils.GetMyPath()) + } + } +} diff --git a/agent/agent/utils/address.go b/agent/utils/address.go similarity index 100% rename from agent/agent/utils/address.go rename to agent/utils/address.go diff --git a/agent/utils/banner.go b/agent/utils/banner.go new file mode 100644 index 000000000..cb7c45f59 --- /dev/null +++ b/agent/utils/banner.go @@ -0,0 +1,17 @@ +package utils + +import "fmt" + +func PrintBanner() { + banner := "\n" + + "..........................................................................\n" + + " _ _ _ _____ _ _ \n" + + " | | | | | | / ____| | | | | \n" + + " | | | | | |_ _ __ ___ | (___ | |_ __ _ ___ | | __ \n" + + " | | | | | __| | '_ ` _ \\ \\___ \\ | __| / _` | / __| | |/ / \n" + + " | |__| | | |_ | | | | | | ____) | | |_ | (_| | | (__ | < \n" + + " \\____/ \\__| |_| |_| |_| |_____/ \\__| \\__,_| \\___| |_|\\_\\ \n" + + ".........................................................................." + + fmt.Println(banner) +} diff --git a/agent/agent/utils/certs.go b/agent/utils/certs.go similarity index 100% rename from agent/agent/utils/certs.go rename to agent/utils/certs.go diff --git a/agent/agent/utils/cmd.go b/agent/utils/cmd.go similarity index 87% rename from agent/agent/utils/cmd.go rename to agent/utils/cmd.go index 2c1543286..e573973ae 100644 --- a/agent/agent/utils/cmd.go +++ b/agent/utils/cmd.go @@ -20,6 +20,9 @@ func ExecuteWithResult(c string, dir string, arg ...string) (string, bool) { return string(out[:]) + err.Error(), true } + if string(out[:]) == "" { + return "Command executed successfully but no output", false + } validUtf8Out, _, err := validations.ValidateString(string(out[:]), false) if err != nil { return string(out[:]) + err.Error(), true diff --git a/agent/agent/utils/crypt.go b/agent/utils/crypt.go similarity index 100% rename from agent/agent/utils/crypt.go rename to agent/utils/crypt.go diff --git a/agent/agent/utils/delay.go b/agent/utils/delay.go similarity index 100% rename from agent/agent/utils/delay.go rename to agent/utils/delay.go diff --git a/agent/utils/download.go b/agent/utils/download.go new file mode 100644 index 000000000..ec350c51e --- /dev/null +++ b/agent/utils/download.go @@ -0,0 +1,53 @@ +package utils + +import ( + "fmt" + "io" + "net/http" + "os" + "path/filepath" +) + +func DownloadFile(url string, headers map[string]string, fileName string, path string, skipTls bool) error { + req, err := http.NewRequest("GET", url, nil) + if err != nil { + return fmt.Errorf("error creating new request: %v", err) + } + for key, value := range headers { + req.Header.Add(key, value) + } + + client := &http.Client{} + if !skipTls { + tlsConfig, err := LoadHTTPTLSCredentials(filepath.Join(GetMyPath(), "certs", "utm.crt")) + if err != nil { + return fmt.Errorf("failed to load TLS credentials: %v", err) + } + client.Transport = &http.Transport{ + TLSClientConfig: tlsConfig, + } + } + + resp, err := client.Do(req) + if err != nil { + return fmt.Errorf("error sending request: %v", err) + } + defer func() { _ = resp.Body.Close() }() + + if resp.StatusCode != http.StatusOK { + return fmt.Errorf("expected status %d; got %d", http.StatusOK, resp.StatusCode) + } + + out, err := os.Create(filepath.Join(path, fileName)) + if err != nil { + return fmt.Errorf("error creating file: %v", err) + } + defer func() { _ = out.Close() }() + + _, err = io.Copy(out, resp.Body) + if err != nil { + return fmt.Errorf("error copying file: %v", err) + } + + return nil +} diff --git a/agent/agent/utils/files.go b/agent/utils/files.go similarity index 68% rename from agent/agent/utils/files.go rename to agent/utils/files.go index 56b9936f7..977b5689c 100644 --- a/agent/agent/utils/files.go +++ b/agent/utils/files.go @@ -12,40 +12,36 @@ import ( "gopkg.in/yaml.v2" ) -// GetMyPath returns the directory path where the currently running executable is located. -// Returns a string representing the directory path, and an error if any error occurs during the process. -func GetMyPath() (string, error) { +func GetMyPath() string { ex, err := os.Executable() if err != nil { - return "", err + return "" } exPath := filepath.Dir(ex) - return exPath, nil + return exPath } -// ReadYAML reads the YAML data from the specified file URL and deserializes it into the provided result interface{}. -// Returns an error if any error occurs during the process. func ReadYAML(path string, result interface{}) error { file, err := os.Open(path) if err != nil { return err } - defer file.Close() + defer func() { _ = file.Close() }() + d := yaml.NewDecoder(file) if err := d.Decode(result); err != nil { return err } + return nil } -func writeToFile(fileName string, body string) error { +func WriteStringToFile(fileName string, body string) error { file, err := os.OpenFile(fileName, os.O_CREATE|os.O_RDWR|os.O_TRUNC, os.ModePerm) - if err != nil { return err } - - defer file.Close() + defer func() { _ = file.Close() }() _, err = file.WriteString(body) return err @@ -57,7 +53,7 @@ func WriteYAML(url string, data interface{}) error { return err } - err = writeToFile(url, string(config[:])) + err = WriteStringToFile(url, string(config)) if err != nil { return err } @@ -71,7 +67,7 @@ func WriteJSON(path string, data interface{}) error { return err } - err = writeToFile(path, string(jsonData[:])) + err = WriteStringToFile(path, string(jsonData)) if err != nil { return err } @@ -84,29 +80,28 @@ func ReadJson(fileName string, data interface{}) error { if err != nil { return err } + err = json.Unmarshal(content, data) if err != nil { return err } + return nil } -func GenerateFromTemplate(data interface{}, tfile string, cfile string) error { - _, fileName := filepath.Split(tfile) - ut, err := template.New(fileName).ParseFiles(tfile) - +func GenerateFromTemplate(data interface{}, templateFile string, configFile string) error { + _, fileName := filepath.Split(templateFile) + ut, err := template.New(fileName).ParseFiles(templateFile) if err != nil { return err } - writer, err := os.OpenFile(cfile, os.O_CREATE|os.O_WRONLY|os.O_TRUNC, os.ModePerm) - + writer, err := os.OpenFile(configFile, os.O_CREATE|os.O_WRONLY|os.O_TRUNC, os.ModePerm) if err != nil { return err } err = ut.Execute(writer, data) - if err != nil { return err } @@ -114,10 +109,9 @@ func GenerateFromTemplate(data interface{}, tfile string, cfile string) error { return nil } -// CreatePathIfNotExist creates a specific path if not exist func CreatePathIfNotExist(path string) error { if _, err := os.Stat(path); os.IsNotExist(err) { - if err := os.Mkdir(path, 0755); err != nil { + if err := os.MkdirAll(path, 0755); err != nil { return fmt.Errorf("error creating path: %v", err) } } else if err != nil { diff --git a/agent/agent/utils/host.go b/agent/utils/host.go similarity index 100% rename from agent/agent/utils/host.go rename to agent/utils/host.go diff --git a/agent/agent/utils/log.go b/agent/utils/log.go similarity index 61% rename from agent/agent/utils/log.go rename to agent/utils/log.go index 14acda6e6..123518653 100644 --- a/agent/agent/utils/log.go +++ b/agent/utils/log.go @@ -1,36 +1,13 @@ package utils import ( - "fmt" "os" "path/filepath" "regexp" - "runtime" "strconv" "time" ) -func SentLog(msg string) error { - // Get current path - path, err := GetMyPath() - if err != nil { - return fmt.Errorf("failed to get current path: %v", err) - } - switch runtime.GOOS { - case "windows": - err := Execute("eventcreate", path, "/T", "INFORMATION", "/ID", "1000", "/SO", "UTMStackAgent", "/D", msg) - if err != nil { - return fmt.Errorf("%v", err) - } - case "linux": - err := Execute("logger", path, "-p", "syslog.info", msg) - if err != nil { - return fmt.Errorf("%v", err) - } - } - return nil -} - func FindLatestLog(path string, pattern *regexp.Regexp) (string, error) { files, err := os.ReadDir(path) if err != nil { diff --git a/agent/utils/logger.go b/agent/utils/logger.go new file mode 100644 index 000000000..1ae428c49 --- /dev/null +++ b/agent/utils/logger.go @@ -0,0 +1,20 @@ +package utils + +import ( + "sync" + + "github.com/threatwinds/logger" +) + +var ( + Logger *logger.Logger + loggerOnceInstance sync.Once +) + +func InitLogger(filename string) { + loggerOnceInstance.Do(func() { + Logger = logger.NewLogger( + &logger.Config{Format: "text", Level: 200, Output: filename, Retries: 3, Wait: 5}, + ) + }) +} diff --git a/agent/agent/utils/os.go b/agent/utils/os.go similarity index 100% rename from agent/agent/utils/os.go rename to agent/utils/os.go diff --git a/agent/utils/port.go b/agent/utils/port.go new file mode 100644 index 000000000..c194e12d5 --- /dev/null +++ b/agent/utils/port.go @@ -0,0 +1,29 @@ +package utils + +import ( + "fmt" + "net" + "time" +) + +func ArePortsReachable(ip string, ports ...string) error { + var conn net.Conn + var err error + +external: + for _, port := range ports { + for i := 0; i < 3; i++ { + conn, err = net.DialTimeout("tcp", fmt.Sprintf("%s:%s", ip, port), 5*time.Second) + if err == nil { + conn.Close() + continue external + } + time.Sleep(5 * time.Second) + } + if err != nil { + return fmt.Errorf("cannot connect to %s on port %s: %v", ip, port, err) + } + } + + return nil +} diff --git a/agent/utils/req.go b/agent/utils/req.go new file mode 100644 index 000000000..9fe861f46 --- /dev/null +++ b/agent/utils/req.go @@ -0,0 +1,58 @@ +package utils + +import ( + "bytes" + "encoding/json" + "fmt" + "io" + "net/http" + "path/filepath" +) + +func DoReq[response any](url string, data []byte, method string, headers map[string]string, skipTlsVerification bool) (response, int, error) { + var result response + + req, err := http.NewRequest(method, url, bytes.NewBuffer(data)) + if err != nil { + return result, http.StatusInternalServerError, err + } + + for k, v := range headers { + req.Header.Add(k, v) + } + + client := &http.Client{} + if !skipTlsVerification { + tlsConfig, err := LoadHTTPTLSCredentials(filepath.Join(GetMyPath(), "certs", "utm.crt")) + if err != nil { + return result, http.StatusInternalServerError, fmt.Errorf("failed to load TLS credentials: %v", err) + } + client.Transport = &http.Transport{ + TLSClientConfig: tlsConfig, + } + } + + resp, err := client.Do(req) + if err != nil { + return result, http.StatusInternalServerError, err + } + defer func() { + _ = resp.Body.Close() + }() + + body, err := io.ReadAll(resp.Body) + if err != nil { + return result, http.StatusInternalServerError, err + } + + if resp.StatusCode != http.StatusAccepted && resp.StatusCode != http.StatusOK { + return result, resp.StatusCode, fmt.Errorf("while sending request to %s received status code: %d and response body: %s", url, resp.StatusCode, body) + } + + err = json.Unmarshal(body, &result) + if err != nil { + return result, http.StatusInternalServerError, err + } + + return result, resp.StatusCode, nil +} diff --git a/agent/installer/utils/service.go b/agent/utils/services.go similarity index 53% rename from agent/installer/utils/service.go rename to agent/utils/services.go index fa7327825..f3faf1191 100644 --- a/agent/installer/utils/service.go +++ b/agent/utils/services.go @@ -2,18 +2,15 @@ package utils import ( "fmt" - "os/exec" + "os" "runtime" ) func StopService(name string) error { - path, err := GetMyPath() - if err != nil { - return err - } + path := GetMyPath() switch runtime.GOOS { case "windows": - err := Execute("cmd", path, "/c", "sc", "stop", name) + err := Execute("sc", path, "stop", name) if err != nil { return fmt.Errorf("error stoping service: %v", err) } @@ -27,13 +24,10 @@ func StopService(name string) error { } func UninstallService(name string) error { - path, err := GetMyPath() - if err != nil { - return err - } + path := GetMyPath() switch runtime.GOOS { case "windows": - err := Execute("cmd", path, "/c", "sc", "delete", name) + err := Execute("sc", path, "delete", name) if err != nil { return fmt.Errorf("error uninstalling service: %v", err) } @@ -52,18 +46,56 @@ func UninstallService(name string) error { // CheckIfServiceIsInstalled checks if a service is installed func CheckIfServiceIsInstalled(serv string) (bool, error) { - var cmd *exec.Cmd + path := GetMyPath() + var err error switch runtime.GOOS { case "windows": - cmd = exec.Command("sc", "query", serv) + err = Execute("sc", path, "query", serv) case "linux": - cmd = exec.Command("systemctl", "status", serv) + err = Execute("systemctl", path, "status", serv) default: return false, fmt.Errorf("operative system unknown") } - if err := cmd.Run(); err != nil { + if err != nil { return false, nil } return true, nil } + +func CreateLinuxService(serviceName string, execStart string) error { + servicePath := "/etc/systemd/system/" + serviceName + ".service" + if !CheckIfPathExist(servicePath) { + file, err := os.Create(servicePath) + if err != nil { + return fmt.Errorf("error creating %s file: %v", servicePath, err) + } + defer func() { _ = file.Close() }() + + serviceContent := fmt.Sprintf(`[Unit] +Description=%s +After=network.target + +[Service] +ExecStart=%s +Restart=always + +[Install] +WantedBy=multi-user.target +`, serviceName, execStart) + + _, err = file.WriteString(serviceContent) + if err != nil { + return err + } + + err = file.Sync() + if err != nil { + return err + } + } else { + return fmt.Errorf("service %s already exists", serviceName) + } + + return nil +} diff --git a/agent/installer/utils/tls.go b/agent/utils/tls.go similarity index 54% rename from agent/installer/utils/tls.go rename to agent/utils/tls.go index 77fc7470e..b60be2ca5 100644 --- a/agent/installer/utils/tls.go +++ b/agent/utils/tls.go @@ -5,10 +5,11 @@ import ( "crypto/x509" "fmt" "os" + + "google.golang.org/grpc/credentials" ) -func LoadTLSCredentials(crtName string) (*tls.Config, error) { - // Load the server's certificate +func LoadHTTPTLSCredentials(crtName string) (*tls.Config, error) { serverCert, err := os.ReadFile(crtName) if err != nil { return nil, err @@ -25,3 +26,12 @@ func LoadTLSCredentials(crtName string) (*tls.Config, error) { return config, nil } + +func LoadGRPCTLSCredentials(crtName string) (credentials.TransportCredentials, error) { + config, err := LoadHTTPTLSCredentials(crtName) + if err != nil { + return nil, err + } + + return credentials.NewTLS(config), nil +} diff --git a/agent/agent/utils/watcher.go b/agent/utils/watcher.go similarity index 85% rename from agent/agent/utils/watcher.go rename to agent/utils/watcher.go index 1b0ae662c..01bb45efe 100644 --- a/agent/agent/utils/watcher.go +++ b/agent/utils/watcher.go @@ -4,13 +4,11 @@ import ( "fmt" "regexp" "time" - - "github.com/threatwinds/logger" ) const maxBatchWait = 5 * time.Second -func TailLogFile(filePath string, logLinesChan chan []string, stopChan chan bool, batchCapacity int, h *logger.Logger) { +func TailLogFile(filePath string, logLinesChan chan []string, stopChan chan bool, batchCapacity int) { latestline := "null" batch := make([]string, 0, batchCapacity) ticker := time.NewTicker(maxBatchWait) @@ -32,7 +30,7 @@ loop: default: lines, err := ReadFileLines(filePath) if err != nil { - h.Info("error reading file %s: %v\n", filePath, err) + Logger.Info("error reading file %s: %v\n", filePath, err) continue } if len(lines) <= 1 { @@ -64,7 +62,7 @@ loop: } } -func WatchFolder(logType string, logsPath string, logLinesChan chan []string, batchCapacity int, h *logger.Logger) { +func WatchFolder(logType string, logsPath string, logLinesChan chan []string, batchCapacity int) { stopChan := make(chan bool) latestLog := "" pattern := regexp.MustCompile(fmt.Sprintf(`%s-(\d+)(?:-(\d+))?\.ndjson`, logType)) @@ -74,13 +72,13 @@ func WatchFolder(logType string, logsPath string, logLinesChan chan []string, ba for range ticker.C { isEmpty, err := IsDirEmpty(logsPath) if err != nil { - h.Info("error checking if %s is empty: %v\n", logsPath, err) + Logger.Info("error checking if %s is empty: %v\n", logsPath, err) continue } if !isEmpty { newLatestLog, err := FindLatestLog(logsPath, pattern) if err != nil { - h.Info("error getting latest log name: %v", err) + Logger.Info("error getting latest log name: %v", err) continue } if newLatestLog != latestLog && newLatestLog != "" { @@ -88,7 +86,7 @@ func WatchFolder(logType string, logsPath string, logLinesChan chan []string, ba stopChan <- true } latestLog = newLatestLog - go TailLogFile(latestLog, logLinesChan, stopChan, batchCapacity, h) + go TailLogFile(latestLog, logLinesChan, stopChan, batchCapacity) } } } diff --git a/agent/installer/utils/unzip.go b/agent/utils/zip.go similarity index 92% rename from agent/installer/utils/unzip.go rename to agent/utils/zip.go index ccd121334..e8c8381b8 100644 --- a/agent/installer/utils/unzip.go +++ b/agent/utils/zip.go @@ -8,7 +8,6 @@ import ( "path/filepath" ) -// Unzip function unzip a zip file to a specified destination path func Unzip(zipFile, destPath string) error { archive, err := zip.OpenReader(zipFile) if err != nil { diff --git a/agent/version.json b/agent/version.json new file mode 100644 index 000000000..641e8961a --- /dev/null +++ b/agent/version.json @@ -0,0 +1,3 @@ +{ + "version": "10.6.0" +} diff --git a/agent/versions.json b/agent/versions.json deleted file mode 100644 index 44e2fcfbf..000000000 --- a/agent/versions.json +++ /dev/null @@ -1,5 +0,0 @@ -{ - "agent_version": "10.5.1", - "updater_version": "10.1.4", - "redline_version": "10.1.2" -} diff --git a/aws/configuration/const.go b/aws/configuration/const.go index d059ca2e7..253d338a6 100644 --- a/aws/configuration/const.go +++ b/aws/configuration/const.go @@ -3,7 +3,8 @@ package configuration import "github.com/utmstack/UTMStack/aws/utils" const ( - CORRELATIONURL = "http://correlation:8080/v1/newlog" + CORRELATIONURL = "http://correlation:8080/v1/newlog" + URL_CHECK_CONNECTION = "https://sts.amazonaws.com" ) func GetInternalKey() string { diff --git a/aws/go.mod b/aws/go.mod index 5ee3687f3..c1bf274f2 100644 --- a/aws/go.mod +++ b/aws/go.mod @@ -6,7 +6,7 @@ toolchain go1.23.4 require ( github.com/aws/aws-sdk-go v1.53.3 - github.com/threatwinds/logger v1.1.12 + github.com/threatwinds/logger v1.2.1 github.com/utmstack/config-client-go v1.2.5 ) diff --git a/aws/go.sum b/aws/go.sum index bc7b79079..7874aefa5 100644 --- a/aws/go.sum +++ b/aws/go.sum @@ -68,8 +68,8 @@ github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= +github.com/threatwinds/logger v1.2.1 h1:uN7efZaHobMX3DRi6GOPtxESPxt5xj0bNflnmgklwII= +github.com/threatwinds/logger v1.2.1/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= diff --git a/aws/main.go b/aws/main.go index 9b0578fda..453e87f67 100644 --- a/aws/main.go +++ b/aws/main.go @@ -23,6 +23,10 @@ func main() { st := time.Now().Add(-600 * time.Second) for { + if err := utils.ConnectionChecker(configuration.URL_CHECK_CONNECTION); err != nil { + utils.Logger.ErrorF("Failed to establish connection: %v", err) + } + et := st.Add(299 * time.Second) moduleConfig, err := client.GetUTMConfig(enum.AWS_IAM_USER) if err != nil { diff --git a/aws/utils/check.go b/aws/utils/check.go new file mode 100644 index 000000000..f7212deb0 --- /dev/null +++ b/aws/utils/check.go @@ -0,0 +1,42 @@ +package utils + +import ( + "fmt" + "net/http" + "time" +) + +func ConnectionChecker(url string) error { + checkConn := func() error { + if err := checkPanelConnection(url); err != nil { + return fmt.Errorf("connection failed: %v", err) + } + + return nil + } + + if err := Logger.InfiniteRetryIfXError(checkConn, "connection failed"); err != nil { + return err + } + + return nil +} + +func checkPanelConnection(url string) error { + client := &http.Client{ + Timeout: 30 * time.Second, + } + + req, err := http.NewRequest(http.MethodGet, url, nil) + if err != nil { + return err + } + + resp, err := client.Do(req) + if err != nil { + return err + } + defer resp.Body.Close() + + return nil +} diff --git a/bitdefender/configuration/config.go b/bitdefender/configuration/config.go index 76f08ccbb..c5eaf7fd6 100644 --- a/bitdefender/configuration/config.go +++ b/bitdefender/configuration/config.go @@ -12,6 +12,7 @@ import ( "github.com/threatwinds/logger" "github.com/utmstack/UTMStack/bitdefender/constants" + "github.com/utmstack/UTMStack/bitdefender/utils" "github.com/utmstack/config-client-go/enum" "github.com/utmstack/config-client-go/types" @@ -29,7 +30,6 @@ const delayCheckConfig = 30 * time.Second var configsSent = make(map[string]ModuleConfig) -// ConfigureModules updates the module configuration every 30 seconds. func ConfigureModules(cnf *types.ConfigurationSection, mutex *sync.Mutex, h *logger.Logger) { intKey := constants.GetInternalKey() panelServ := constants.GetPanelServiceName() @@ -37,7 +37,10 @@ func ConfigureModules(cnf *types.ConfigurationSection, mutex *sync.Mutex, h *log for { time.Sleep(delayCheckConfig) - // Get Bitdefender module configs + if err := utils.ConnectionChecker(constants.URL_CHECK_CONNECTION, h); err != nil { + h.ErrorF("Failed to establish connection: %v", err) + } + tempModuleConfig, err := client.GetUTMConfig(enum.BITDEFENDER) if err != nil { if strings.Contains(err.Error(), "invalid character '<'") { @@ -52,7 +55,6 @@ func ConfigureModules(cnf *types.ConfigurationSection, mutex *sync.Mutex, h *log *cnf = *tempModuleConfig mutex.Unlock() - // Configure the group to send data to the syslog server if it is not already configured for _, group := range (*cnf).ConfigurationGroups { isNecessaryConfig := compareConfigs(configsSent, group) if isNecessaryConfig { @@ -84,9 +86,6 @@ func ConfigureModules(cnf *types.ConfigurationSection, mutex *sync.Mutex, h *log } } -// confBDGZApiPush configures the Bitdefender API. -// It checks to check that everything has been configured correctly. -// Send test logs func confBDGZApiPush(config types.ModuleGroup, operation string, h *logger.Logger) error { operationFunc := map[string]func(types.ModuleGroup, *logger.Logger) (*http.Response, error){ "sendConf": sendPushEventSettings, @@ -112,7 +111,6 @@ func confBDGZApiPush(config types.ModuleGroup, operation string, h *logger.Logge h.Info(string(myBody)) if operation == "sendConf" { - // Check if config was sent correctly regex := regexp.MustCompile(`result":true`) match := regex.Match([]byte(string(myBody))) if match { @@ -124,7 +122,6 @@ func confBDGZApiPush(config types.ModuleGroup, operation string, h *logger.Logge return fmt.Errorf("error sending configuration") } -// setPushEventSettings sends the configuration to the Bitdefender API func sendPushEventSettings(config types.ModuleGroup, h *logger.Logger) (*http.Response, error) { h.Info("Sending configuration...") byteTemplate := getTemplateSetPush(config) @@ -136,7 +133,6 @@ func sendPushEventSettings(config types.ModuleGroup, h *logger.Logger) (*http.Re return sendRequest(body, config) } -// getPushEventSettings gets the Bitdefender API settings func getPushEventSettings(config types.ModuleGroup, h *logger.Logger) (*http.Response, error) { h.Info("Checking configuration...") byteTemplate := getTemplateGet() @@ -148,7 +144,6 @@ func getPushEventSettings(config types.ModuleGroup, h *logger.Logger) (*http.Res return sendRequest(body, config) } -// sendTestPushEvent sends a test event to the connector func sendTestPushEvent(config types.ModuleGroup, h *logger.Logger) (*http.Response, error) { h.Info("Sending Event Test...") byteTemplate := getTemplateTest() diff --git a/bitdefender/constants/const.go b/bitdefender/constants/const.go index c4fa37102..16455fc95 100644 --- a/bitdefender/constants/const.go +++ b/bitdefender/constants/const.go @@ -4,6 +4,8 @@ import "github.com/utmstack/UTMStack/bitdefender/utils" const EndpointPush = "/v1.0/jsonrpc/push" +const URL_CHECK_CONNECTION = "https://cloud.gravityzone.bitdefender.com" + func GetInternalKey() string { return utils.Getenv("INTERNAL_KEY") } diff --git a/bitdefender/go.mod b/bitdefender/go.mod index 7216bcc7d..4bd7c06cf 100644 --- a/bitdefender/go.mod +++ b/bitdefender/go.mod @@ -7,7 +7,7 @@ toolchain go1.23.4 require ( github.com/RackSec/srslog v0.0.0-20180709174129-a4725f04ec91 github.com/gorilla/mux v1.8.1 - github.com/threatwinds/logger v1.1.12 + github.com/threatwinds/logger v1.2.1 github.com/utmstack/config-client-go v1.2.6 ) diff --git a/bitdefender/go.sum b/bitdefender/go.sum index 2ffb7bda8..94667b761 100644 --- a/bitdefender/go.sum +++ b/bitdefender/go.sum @@ -66,8 +66,8 @@ github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= +github.com/threatwinds/logger v1.2.1 h1:uN7efZaHobMX3DRi6GOPtxESPxt5xj0bNflnmgklwII= +github.com/threatwinds/logger v1.2.1/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= diff --git a/bitdefender/utils/check.go b/bitdefender/utils/check.go new file mode 100644 index 000000000..a39840a2f --- /dev/null +++ b/bitdefender/utils/check.go @@ -0,0 +1,43 @@ +package utils + +import ( + "fmt" + "net/http" + "time" + + "github.com/threatwinds/logger" +) + +func ConnectionChecker(url string, h *logger.Logger) error { + checkConn := func() error { + if err := CheckConnection(url); err != nil { + return fmt.Errorf("connection failed: %v", err) + } + return nil + } + + if err := h.InfiniteRetryIfXError(checkConn, "connection failed"); err != nil { + return err + } + + return nil +} + +func CheckConnection(url string) error { + client := &http.Client{ + Timeout: 30 * time.Second, + } + + req, err := http.NewRequest(http.MethodGet, url, nil) + if err != nil { + return err + } + + resp, err := client.Do(req) + if err != nil { + return err + } + defer resp.Body.Close() + + return nil +} diff --git a/correlation/rules/update.go b/correlation/rules/update.go index f79caabae..a3ec628c9 100644 --- a/correlation/rules/update.go +++ b/correlation/rules/update.go @@ -12,9 +12,20 @@ import ( func Update(updateReady chan bool) { first := true for { - log.Println("Downloading rules") cnf := utils.GetConfig() + if cnf.ConnectionMode == utils.ConnModeOffline { + if _, err := os.Stat(cnf.RulesFolder + "system"); err == nil { + log.Println("Offline mode: rules folder exists, skipping git clone") + if first { + first = false + updateReady <- true + } + time.Sleep(48 * time.Hour) + continue + } + } + f, err := os.Stat(cnf.RulesFolder + "system") if err != nil { if !errors.Is(err, os.ErrNotExist) { diff --git a/correlation/utils/configuration.go b/correlation/utils/configuration.go index 01967734e..8e8037aad 100644 --- a/correlation/utils/configuration.go +++ b/correlation/utils/configuration.go @@ -4,7 +4,7 @@ import ( "sync" ) -type Config struct { +type YamlConfig struct { RulesFolder string `yaml:"rulesFolder"` Elasticsearch string `yaml:"elasticsearch"` Postgres struct { @@ -17,11 +17,28 @@ type Config struct { ErrorLevel string `yaml:"errorLevel"` } +type ConnMode string + +const ( + ConnModeOffline ConnMode = "OFFLINE" + ConnModeOnline ConnMode = "ONLINE" +) + +type EnvVarConfig struct { + ConnectionMode ConnMode `env:"CONNECTION_MODE"` +} + +type Config struct { + YamlConfig + EnvVarConfig +} + var oneConfigRead sync.Once var cnf Config func readConfig() { - ReadYaml("config.yml", &cnf) + ReadYaml("config.yml", &cnf.YamlConfig) + ReadEnvVars(&cnf.EnvVarConfig) } func GetConfig() Config { diff --git a/correlation/utils/readers.go b/correlation/utils/readers.go index c70a0e974..5e4e89732 100644 --- a/correlation/utils/readers.go +++ b/correlation/utils/readers.go @@ -4,6 +4,9 @@ import ( "encoding/csv" "log" "os" + "reflect" + "strconv" + "strings" "gopkg.in/yaml.v3" ) @@ -33,3 +36,69 @@ func ReadCSV(url string) [][]string { } return result } + +func ReadEnvVars(cfg interface{}) { + v := reflect.ValueOf(cfg).Elem() + t := v.Type() + + for i := 0; i < t.NumField(); i++ { + field := t.Field(i) + envTag := field.Tag.Get("env") + if envTag == "" { + continue + } + + // Check if the environment variable exists + envValue, exists := os.LookupEnv(envTag) + if !exists { + log.Printf("Environment variable %s not set, skipping...", envTag) + continue + } + + fieldValue := v.Field(i) + if !fieldValue.CanSet() { + log.Printf("Cannot set field %s, skipping...", field.Name) + continue + } + + switch fieldValue.Kind() { + case reflect.String: + fieldValue.SetString(envValue) + case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64: + if intValue, err := strconv.ParseInt(envValue, 10, fieldValue.Type().Bits()); err == nil { + fieldValue.SetInt(intValue) + } else { + log.Printf("Failed to convert %s to int for field %s: %v", envValue, field.Name, err) + } + case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64: + if uintValue, err := strconv.ParseUint(envValue, 10, fieldValue.Type().Bits()); err == nil { + fieldValue.SetUint(uintValue) + } else { + log.Printf("Failed to convert %s to uint for field %s: %v", envValue, field.Name, err) + } + case reflect.Float32, reflect.Float64: + if floatValue, err := strconv.ParseFloat(envValue, fieldValue.Type().Bits()); err == nil { + fieldValue.SetFloat(floatValue) + } else { + log.Printf("Failed to convert %s to float for field %s: %v", envValue, field.Name, err) + } + case reflect.Bool: + if boolValue, err := strconv.ParseBool(envValue); err == nil { + fieldValue.SetBool(boolValue) + } else { + log.Printf("Failed to convert %s to bool for field %s: %v", envValue, field.Name, err) + } + case reflect.Slice: + elements := reflect.MakeSlice(fieldValue.Type(), 0, 0) + for _, elem := range strings.Split(envValue, ",") { + elements = reflect.Append(elements, reflect.ValueOf(elem)) + } + fieldValue.Set(elements) + case reflect.Ptr: + ptr := reflect.New(fieldValue.Type().Elem()) + fieldValue.Set(ptr) + default: + log.Printf("Unsupported field type %s for field %s", fieldValue.Kind(), field.Name) + } + } +} diff --git a/installer/types/compose.go b/installer/types/compose.go index ce7b44769..2be5383f2 100644 --- a/installer/types/compose.go +++ b/installer/types/compose.go @@ -442,6 +442,7 @@ func (c *Compose) Populate(conf *Config, stack *StackConfig) *Compose { "ELASTICSEARCH_HOST=node1", "ELASTICSEARCH_PORT=9200", "ERROR_LEVEL=info", + "CONNECTION_MODE=ONLINE", }, Logging: &dLogging, Deploy: &Deploy{ diff --git a/log-auth-proxy/go.mod b/log-auth-proxy/go.mod index d06b549c1..338ff0aa3 100644 --- a/log-auth-proxy/go.mod +++ b/log-auth-proxy/go.mod @@ -1,13 +1,13 @@ module github.com/utmstack/UTMStack/log-auth-proxy -go 1.22.4 +go 1.23.0 toolchain go1.23.4 require ( github.com/gin-gonic/gin v1.10.0 - github.com/threatwinds/logger v1.1.12 - google.golang.org/grpc v1.70.0 + github.com/threatwinds/logger v1.2.1 + google.golang.org/grpc v1.71.0 google.golang.org/protobuf v1.36.5 ) @@ -33,11 +33,11 @@ require ( github.com/twitchyliquid64/golang-asm v0.15.1 // indirect github.com/ugorji/go/codec v1.2.12 // indirect golang.org/x/arch v0.9.0 // indirect - golang.org/x/crypto v0.30.0 // indirect - golang.org/x/net v0.32.0 // indirect - golang.org/x/sys v0.28.0 // indirect - golang.org/x/text v0.21.0 // indirect - google.golang.org/genproto/googleapis/rpc v0.0.0-20241202173237-19429a94021a // indirect + golang.org/x/crypto v0.36.0 // indirect + golang.org/x/net v0.37.0 // indirect + golang.org/x/sys v0.31.0 // indirect + golang.org/x/text v0.23.0 // indirect + google.golang.org/genproto/googleapis/rpc v0.0.0-20250115164207-1a7da9e5054f // indirect gopkg.in/natefinch/lumberjack.v2 v2.2.1 // indirect gopkg.in/yaml.v3 v3.0.1 // indirect ) diff --git a/log-auth-proxy/go.sum b/log-auth-proxy/go.sum index fb16a837c..833a01eca 100644 --- a/log-auth-proxy/go.sum +++ b/log-auth-proxy/go.sum @@ -68,38 +68,40 @@ github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= +github.com/threatwinds/logger v1.2.1 h1:uN7efZaHobMX3DRi6GOPtxESPxt5xj0bNflnmgklwII= +github.com/threatwinds/logger v1.2.1/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= github.com/ugorji/go/codec v1.2.12/go.mod h1:UNopzCgEMSXjBc6AOMqYvWC1ktqTAfzJZUZgYf6w6lg= -go.opentelemetry.io/otel v1.32.0 h1:WnBN+Xjcteh0zdk01SVqV55d/m62NJLJdIyb4y/WO5U= -go.opentelemetry.io/otel v1.32.0/go.mod h1:00DCVSB0RQcnzlwyTfqtxSm+DRr9hpYrHjNGiBHVQIg= -go.opentelemetry.io/otel/metric v1.32.0 h1:xV2umtmNcThh2/a/aCP+h64Xx5wsj8qqnkYZktzNa0M= -go.opentelemetry.io/otel/metric v1.32.0/go.mod h1:jH7CIbbK6SH2V2wE16W05BHCtIDzauciCRLoc/SyMv8= -go.opentelemetry.io/otel/sdk v1.32.0 h1:RNxepc9vK59A8XsgZQouW8ue8Gkb4jpWtJm9ge5lEG4= -go.opentelemetry.io/otel/sdk v1.32.0/go.mod h1:LqgegDBjKMmb2GC6/PrTnteJG39I8/vJCAP9LlJXEjU= -go.opentelemetry.io/otel/sdk/metric v1.32.0 h1:rZvFnvmvawYb0alrYkjraqJq0Z4ZUJAiyYCU9snn1CU= -go.opentelemetry.io/otel/sdk/metric v1.32.0/go.mod h1:PWeZlq0zt9YkYAp3gjKZ0eicRYvOh1Gd+X99x6GHpCQ= -go.opentelemetry.io/otel/trace v1.32.0 h1:WIC9mYrXf8TmY/EXuULKc8hR17vE+Hjv2cssQDe03fM= -go.opentelemetry.io/otel/trace v1.32.0/go.mod h1:+i4rkvCraA+tG6AzwloGaCtkx53Fa+L+V8e9a7YvhT8= +go.opentelemetry.io/auto/sdk v1.1.0 h1:cH53jehLUN6UFLY71z+NDOiNJqDdPRaXzTel0sJySYA= +go.opentelemetry.io/auto/sdk v1.1.0/go.mod h1:3wSPjt5PWp2RhlCcmmOial7AvC4DQqZb7a7wCow3W8A= +go.opentelemetry.io/otel v1.34.0 h1:zRLXxLCgL1WyKsPVrgbSdMN4c0FMkDAskSTQP+0hdUY= +go.opentelemetry.io/otel v1.34.0/go.mod h1:OWFPOQ+h4G8xpyjgqo4SxJYdDQ/qmRH+wivy7zzx9oI= +go.opentelemetry.io/otel/metric v1.34.0 h1:+eTR3U0MyfWjRDhmFMxe2SsW64QrZ84AOhvqS7Y+PoQ= +go.opentelemetry.io/otel/metric v1.34.0/go.mod h1:CEDrp0fy2D0MvkXE+dPV7cMi8tWZwX3dmaIhwPOaqHE= +go.opentelemetry.io/otel/sdk v1.34.0 h1:95zS4k/2GOy069d321O8jWgYsW3MzVV+KuSPKp7Wr1A= +go.opentelemetry.io/otel/sdk v1.34.0/go.mod h1:0e/pNiaMAqaykJGKbi+tSjWfNNHMTxoC9qANsCzbyxU= +go.opentelemetry.io/otel/sdk/metric v1.34.0 h1:5CeK9ujjbFVL5c1PhLuStg1wxA7vQv7ce1EK0Gyvahk= +go.opentelemetry.io/otel/sdk/metric v1.34.0/go.mod h1:jQ/r8Ze28zRKoNRdkjCZxfs6YvBTG1+YIqyFVFYec5w= +go.opentelemetry.io/otel/trace v1.34.0 h1:+ouXS2V8Rd4hp4580a8q23bg0azF2nI8cqLYnC8mh/k= +go.opentelemetry.io/otel/trace v1.34.0/go.mod h1:Svm7lSjQD7kG7KJ/MUHPVXSDGz2OX4h0M2jHBhmSfRE= golang.org/x/arch v0.9.0 h1:ub9TgUInamJ8mrZIGlBG6/4TqWeMszd4N8lNorbrr6k= golang.org/x/arch v0.9.0/go.mod h1:FEVrYAQjsQXMVJ1nsMoVVXPZg6p2JE2mx8psSWTDQys= -golang.org/x/crypto v0.30.0 h1:RwoQn3GkWiMkzlX562cLB7OxWvjH1L8xutO2WoJcRoY= -golang.org/x/crypto v0.30.0/go.mod h1:kDsLvtWBEx7MV9tJOj9bnXsPbxwJQ6csT/x4KIN4Ssk= -golang.org/x/net v0.32.0 h1:ZqPmj8Kzc+Y6e0+skZsuACbx+wzMgo5MQsJh9Qd6aYI= -golang.org/x/net v0.32.0/go.mod h1:CwU0IoeOlnQQWJ6ioyFrfRuomB8GKF6KbYXZVyeXNfs= +golang.org/x/crypto v0.36.0 h1:AnAEvhDddvBdpY+uR+MyHmuZzzNqXSe/GvuDeob5L34= +golang.org/x/crypto v0.36.0/go.mod h1:Y4J0ReaxCR1IMaabaSMugxJES1EpwhBHhv2bDHklZvc= +golang.org/x/net v0.37.0 h1:1zLorHbz+LYj7MQlSf1+2tPIIgibq2eL5xkrGk6f+2c= +golang.org/x/net v0.37.0/go.mod h1:ivrbrMbzFq5J41QOQh0siUuly180yBYtLp+CKbEaFx8= golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.28.0 h1:Fksou7UEQUWlKvIdsqzJmUmCX3cZuD2+P3XyyzwMhlA= -golang.org/x/sys v0.28.0/go.mod h1:/VUhepiaJMQUp4+oa/7Zr1D23ma6VTLIYjOOTFZPUcA= -golang.org/x/text v0.21.0 h1:zyQAAkrwaneQ066sspRyJaG9VNi/YJ1NfzcGB3hZ/qo= -golang.org/x/text v0.21.0/go.mod h1:4IBbMaMmOPCJ8SecivzSH54+73PCFmPWxNTLm+vZkEQ= -google.golang.org/genproto/googleapis/rpc v0.0.0-20241202173237-19429a94021a h1:hgh8P4EuoxpsuKMXX/To36nOFD7vixReXgn8lPGnt+o= -google.golang.org/genproto/googleapis/rpc v0.0.0-20241202173237-19429a94021a/go.mod h1:5uTbfoYQed2U9p3KIj2/Zzm02PYhndfdmML0qC3q3FU= -google.golang.org/grpc v1.70.0 h1:pWFv03aZoHzlRKHWicjsZytKAiYCtNS0dHbXnIdq7jQ= -google.golang.org/grpc v1.70.0/go.mod h1:ofIJqVKDXx/JiXrwr2IG4/zwdH9txy3IlF40RmcJSQw= +golang.org/x/sys v0.31.0 h1:ioabZlmFYtWhL+TRYpcnNlLwhyxaM9kWTDEmfnprqik= +golang.org/x/sys v0.31.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k= +golang.org/x/text v0.23.0 h1:D71I7dUrlY+VX0gQShAThNGHFxZ13dGLBHQLVl1mJlY= +golang.org/x/text v0.23.0/go.mod h1:/BLNzu4aZCJ1+kcD0DNRotWKage4q2rGVAg4o22unh4= +google.golang.org/genproto/googleapis/rpc v0.0.0-20250115164207-1a7da9e5054f h1:OxYkA3wjPsZyBylwymxSHa7ViiW1Sml4ToBrncvFehI= +google.golang.org/genproto/googleapis/rpc v0.0.0-20250115164207-1a7da9e5054f/go.mod h1:+2Yz8+CLJbIfL9z73EW45avw8Lmge3xVElCP9zEKi50= +google.golang.org/grpc v1.71.0 h1:kF77BGdPTQ4/JZWMlb9VpJ5pa25aqvVqogsxNHHdeBg= +google.golang.org/grpc v1.71.0/go.mod h1:H0GRtasmQOh9LkFoCPDu3ZrwUtD1YGE+b2vYBYd/8Ec= google.golang.org/protobuf v1.36.5 h1:tPhr+woSbjfYvY6/GPufUoYizxw1cF/yFoxJ2fmpwlM= google.golang.org/protobuf v1.36.5/go.mod h1:9fA7Ob0pmnwhb644+1+CVWFRbNajQ6iRojtC/QF5bRE= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= diff --git a/office365/configuration/const.go b/office365/configuration/const.go index 1457ee524..05dca1fec 100644 --- a/office365/configuration/const.go +++ b/office365/configuration/const.go @@ -7,7 +7,7 @@ import ( ) const ( - loginUrl = "https://login.microsoftonline.com/" + LoginUrl = "https://login.microsoftonline.com/" GRANTTYPE = "client_credentials" SCOPE = "https://manage.office.com/.default" endPointLogin = "/oauth2/v2.0/token" @@ -26,7 +26,7 @@ func GetPanelServiceName() string { } func GetMicrosoftLoginLink(tenant string) string { - return fmt.Sprintf("%s%s%s", loginUrl, tenant, endPointLogin) + return fmt.Sprintf("%s%s%s", LoginUrl, tenant, endPointLogin) } func GetStartSubscriptionLink(tenant string) string { diff --git a/office365/go.mod b/office365/go.mod index 8f812c791..50cb46971 100644 --- a/office365/go.mod +++ b/office365/go.mod @@ -5,7 +5,7 @@ go 1.22.4 toolchain go1.23.4 require ( - github.com/threatwinds/logger v1.1.12 + github.com/threatwinds/logger v1.2.1 github.com/utmstack/config-client-go v1.2.6 ) diff --git a/office365/go.sum b/office365/go.sum index 42620c96e..7861b7859 100644 --- a/office365/go.sum +++ b/office365/go.sum @@ -62,8 +62,8 @@ github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= +github.com/threatwinds/logger v1.2.1 h1:uN7efZaHobMX3DRi6GOPtxESPxt5xj0bNflnmgklwII= +github.com/threatwinds/logger v1.2.1/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= diff --git a/office365/main.go b/office365/main.go index 2b0d7d271..d59c98304 100644 --- a/office365/main.go +++ b/office365/main.go @@ -23,6 +23,10 @@ func main() { st := time.Now().Add(-600 * time.Second) for { + if err := utils.ConnectionChecker(configuration.LoginUrl); err != nil { + utils.Logger.ErrorF("External connection failure detected: %v", err) + } + et := st.Add(299 * time.Second) startTime := st.UTC().Format("2006-01-02T15:04:05") endTime := et.UTC().Format("2006-01-02T15:04:05") diff --git a/office365/utils/check.go b/office365/utils/check.go new file mode 100644 index 000000000..5ab7c1ccd --- /dev/null +++ b/office365/utils/check.go @@ -0,0 +1,45 @@ +package utils + +import ( + "context" + "fmt" + "net/http" + "time" +) + +const connectionTimeout = 5 * time.Second + +func ConnectionChecker(url string) error { + checkConn := func() error { + ctx, cancel := context.WithTimeout(context.Background(), connectionTimeout) + defer cancel() + + if err := checkConnection(url, ctx); err != nil { + return fmt.Errorf("connection failed") + } + return nil + } + + if err := Logger.InfiniteRetryIfXError(checkConn, "connection failed"); err != nil { + return err + } + + return nil +} + +func checkConnection(url string, ctx context.Context) error { + client := &http.Client{} + + req, err := http.NewRequestWithContext(ctx, http.MethodGet, url, nil) + if err != nil { + return err + } + + resp, err := client.Do(req) + if err != nil { + return err + } + defer resp.Body.Close() + + return nil +} diff --git a/sophos/configuration/const.go b/sophos/configuration/const.go index ce3e6275a..769ab4f6c 100644 --- a/sophos/configuration/const.go +++ b/sophos/configuration/const.go @@ -6,6 +6,7 @@ const ( CORRELATIONURL = "http://correlation:8080/v1/newlog" AUTHURL = "https://id.sophos.com/api/v2/oauth2/token" WHOAMIURL = "https://api.central.sophos.com/whoami/v1" + CHECKCON = "https://id.sophos.com" ) func GetInternalKey() string { diff --git a/sophos/go.mod b/sophos/go.mod index 3b23841c2..798453c23 100644 --- a/sophos/go.mod +++ b/sophos/go.mod @@ -5,7 +5,7 @@ go 1.22.4 toolchain go1.23.4 require ( - github.com/threatwinds/logger v1.1.12 + github.com/threatwinds/logger v1.2.1 github.com/utmstack/config-client-go v1.2.6 ) diff --git a/sophos/go.sum b/sophos/go.sum index 42620c96e..7861b7859 100644 --- a/sophos/go.sum +++ b/sophos/go.sum @@ -62,8 +62,8 @@ github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo= github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg= github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY= -github.com/threatwinds/logger v1.1.12 h1:3TzwO2+m5XwSHDc3QOYvg0nUnsj/U2yJppULndRzL/4= -github.com/threatwinds/logger v1.1.12/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= +github.com/threatwinds/logger v1.2.1 h1:uN7efZaHobMX3DRi6GOPtxESPxt5xj0bNflnmgklwII= +github.com/threatwinds/logger v1.2.1/go.mod h1:eevkhjP9wSpRekRIgi4ZAq7DMdlUMy+Shwx/QNDvOHg= github.com/twitchyliquid64/golang-asm v0.15.1 h1:SU5vSMR7hnwNxj24w34ZyCi/FmDZTkS4MhqMhdFk5YI= github.com/twitchyliquid64/golang-asm v0.15.1/go.mod h1:a1lVb/DtPvCB8fslRZhAngC2+aY1QWCk3Cedj/Gdt08= github.com/ugorji/go/codec v1.2.12 h1:9LC83zGrHhuUA9l16C9AHXAqEV/2wBQ4nkvumAE65EE= diff --git a/sophos/main.go b/sophos/main.go index 9ecb81056..2fc387f04 100644 --- a/sophos/main.go +++ b/sophos/main.go @@ -21,6 +21,10 @@ func main() { client := utmconf.NewUTMClient(intKey, "http://"+panelServ) for { + if err := utils.ConnectionChecker(configuration.CHECKCON); err != nil { + utils.Logger.ErrorF("External connection failure detected: %v", err) + } + moduleConfig, err := client.GetUTMConfig(enum.SOPHOS) if err != nil { if strings.Contains(err.Error(), "invalid character '<'") { diff --git a/sophos/utils/check.go b/sophos/utils/check.go new file mode 100644 index 000000000..5ab7c1ccd --- /dev/null +++ b/sophos/utils/check.go @@ -0,0 +1,45 @@ +package utils + +import ( + "context" + "fmt" + "net/http" + "time" +) + +const connectionTimeout = 5 * time.Second + +func ConnectionChecker(url string) error { + checkConn := func() error { + ctx, cancel := context.WithTimeout(context.Background(), connectionTimeout) + defer cancel() + + if err := checkConnection(url, ctx); err != nil { + return fmt.Errorf("connection failed") + } + return nil + } + + if err := Logger.InfiniteRetryIfXError(checkConn, "connection failed"); err != nil { + return err + } + + return nil +} + +func checkConnection(url string, ctx context.Context) error { + client := &http.Client{} + + req, err := http.NewRequestWithContext(ctx, http.MethodGet, url, nil) + if err != nil { + return err + } + + resp, err := client.Do(req) + if err != nil { + return err + } + defer resp.Body.Close() + + return nil +} diff --git a/version.yml b/version.yml index 23251a8ee..aa72feb11 100644 --- a/version.yml +++ b/version.yml @@ -1 +1 @@ -version: 10.6.2 \ No newline at end of file +version: 10.6.3 \ No newline at end of file