예제 #1
0
def run_script(request):
    agent = get_object_or_404(Agent, pk=request.data["pk"])
    script = get_object_or_404(Script, pk=request.data["scriptPK"])
    output = request.data["output"]
    args = request.data["args"]
    req_timeout = int(request.data["timeout"]) + 3

    AuditLog.audit_script_run(
        username=request.user.username,
        hostname=agent.hostname,
        script=script.name,
    )

    if output == "wait":
        r = agent.run_script(scriptpk=script.pk,
                             args=args,
                             timeout=req_timeout,
                             wait=True)
        return Response(r)

    elif output == "email":
        emails = ([] if request.data["emailmode"] == "default" else
                  request.data["emails"])
        run_script_email_results_task.delay(
            agentpk=agent.pk,
            scriptpk=script.pk,
            nats_timeout=req_timeout,
            emails=emails,
            args=args,
        )
    else:
        agent.run_script(scriptpk=script.pk, args=args, timeout=req_timeout)

    return Response(f"{script.name} will now be run on {agent.hostname}")
예제 #2
0
def meshcentral(request, pk):
    agent = get_object_or_404(Agent, pk=pk)
    core = CoreSettings.objects.first()

    token = agent.get_login_token(key=core.mesh_token,
                                  user=f"user//{core.mesh_username}")

    if token == "err":
        return notify_error("Invalid mesh token")

    control = f"{core.mesh_site}/?login={token}&gotonode={agent.mesh_node_id}&viewmode=11&hide=31"
    terminal = f"{core.mesh_site}/?login={token}&gotonode={agent.mesh_node_id}&viewmode=12&hide=31"
    file = f"{core.mesh_site}/?login={token}&gotonode={agent.mesh_node_id}&viewmode=13&hide=31"

    AuditLog.audit_mesh_session(username=request.user.username,
                                hostname=agent.hostname)

    ret = {
        "hostname": agent.hostname,
        "control": control,
        "terminal": terminal,
        "file": file,
        "status": agent.status,
        "client": agent.client.name,
        "site": agent.site.name,
    }
    return Response(ret)
예제 #3
0
def send_raw_cmd(request):
    agent = get_object_or_404(Agent, pk=request.data["pk"])
    if not agent.has_nats:
        return notify_error("Requires agent version 1.1.0 or greater")
    timeout = int(request.data["timeout"])
    data = {
        "func": "rawcmd",
        "timeout": timeout,
        "payload": {
            "command": request.data["cmd"],
            "shell": request.data["shell"],
        },
    }
    r = asyncio.run(agent.nats_cmd(data, timeout=timeout + 2))

    if r == "timeout":
        return notify_error("Unable to contact the agent")

    AuditLog.audit_raw_command(
        username=request.user.username,
        hostname=agent.hostname,
        cmd=request.data["cmd"],
        shell=request.data["shell"],
    )

    return Response(r)
예제 #4
0
def run_script(request):
    agent = get_object_or_404(Agent, pk=request.data["pk"])
    if not agent.has_nats:
        return notify_error("Requires agent version 1.1.0 or greater")
    script = get_object_or_404(Script, pk=request.data["scriptPK"])
    output = request.data["output"]
    req_timeout = int(request.data["timeout"]) + 3

    AuditLog.audit_script_run(
        username=request.user.username,
        hostname=agent.hostname,
        script=script.name,
    )

    data = {
        "func": "runscript",
        "timeout": request.data["timeout"],
        "script_args": request.data["args"],
        "payload": {
            "code": script.code,
            "shell": script.shell,
        },
    }

    if output == "wait":
        r = asyncio.run(agent.nats_cmd(data, timeout=req_timeout))
        return Response(r)
    else:
        asyncio.run(agent.nats_cmd(data, wait=False))
        return Response(f"{script.name} will now be run on {agent.hostname}")
예제 #5
0
def send_raw_cmd(request):
    agent = get_object_or_404(Agent, pk=request.data["pk"])

    r = agent.salt_api_cmd(
        timeout=request.data["timeout"],
        func="cmd.run",
        kwargs={
            "cmd": request.data["cmd"],
            "shell": request.data["shell"],
            "timeout": request.data["timeout"],
        },
    )

    if r == "timeout":
        return notify_error("Unable to contact the agent")
    elif r == "error" or not r:
        return notify_error("Something went wrong")

    AuditLog.audit_raw_command(
        username=request.user.username,
        hostname=agent.hostname,
        cmd=request.data["cmd"],
        shell=request.data["shell"],
    )

    logger.info(f"The command {request.data['cmd']} was sent on agent {agent.hostname}")
    return Response(r)
예제 #6
0
def run_script(request):
    agent = get_object_or_404(Agent, pk=request.data["pk"])
    script = get_object_or_404(Script, pk=request.data["scriptPK"])

    output = request.data["output"]
    args = request.data["args"]

    req_timeout = int(request.data["timeout"]) + 3

    AuditLog.audit_script_run(
        username=request.user.username,
        hostname=agent.hostname,
        script=script.name,
    )

    if output == "wait":
        r = agent.salt_api_cmd(
            timeout=req_timeout,
            func="win_agent.run_script",
            kwargs={
                "filepath": script.filepath,
                "filename": script.filename,
                "shell": script.shell,
                "timeout": request.data["timeout"],
                "args": args,
            },
        )

        if isinstance(r, dict):
            if r["stdout"]:
                return Response(r["stdout"])
            elif r["stderr"]:
                return Response(r["stderr"])
            else:
                try:
                    r["retcode"]
                except KeyError:
                    return notify_error("Something went wrong")

                return Response(f"Return code: {r['retcode']}")

        else:
            if r == "timeout":
                return notify_error("Unable to contact the agent")
            elif r == "error":
                return notify_error("Something went wrong")
            else:
                return notify_error(str(r))

    else:
        data = {
            "agentpk": agent.pk,
            "scriptpk": script.pk,
            "timeout": request.data["timeout"],
            "args": args,
        }
        run_script_bg_task.delay(data)
        return Response(f"{script.name} will now be run on {agent.hostname}")
예제 #7
0
def bulk(request):
    if request.data["target"] == "agents" and not request.data["agentPKs"]:
        return notify_error("Must select at least 1 agent")

    if request.data["target"] == "client":
        q = Agent.objects.filter(site__client_id=request.data["client"])
    elif request.data["target"] == "site":
        q = Agent.objects.filter(site_id=request.data["site"])
    elif request.data["target"] == "agents":
        q = Agent.objects.filter(pk__in=request.data["agentPKs"])
    elif request.data["target"] == "all":
        q = Agent.objects.only("pk", "monitoring_type")
    else:
        return notify_error("Something went wrong")

    if request.data["monType"] == "servers":
        q = q.filter(monitoring_type="server")
    elif request.data["monType"] == "workstations":
        q = q.filter(monitoring_type="workstation")

    agents: list[int] = [agent.pk for agent in q]

    AuditLog.audit_bulk_action(request.user, request.data["mode"],
                               request.data)

    if request.data["mode"] == "command":
        handle_bulk_command_task.delay(agents, request.data["cmd"],
                                       request.data["shell"],
                                       request.data["timeout"])
        return Response(f"Command will now be run on {len(agents)} agents")

    elif request.data["mode"] == "script":
        script = get_object_or_404(Script, pk=request.data["scriptPK"])
        handle_bulk_script_task.delay(script.pk, agents, request.data["args"],
                                      request.data["timeout"])
        return Response(
            f"{script.name} will now be run on {len(agents)} agents")

    elif request.data["mode"] == "install":
        bulk_install_updates_task.delay(agents)
        return Response(
            f"Pending updates will now be installed on {len(agents)} agents")
    elif request.data["mode"] == "scan":
        bulk_check_for_updates_task.delay(agents)
        return Response(
            f"Patch status scan will now run on {len(agents)} agents")

    return notify_error("Something went wrong")
예제 #8
0
def bulk(request):
    if request.data["target"] == "agents" and not request.data["agentPKs"]:
        return notify_error("Must select at least 1 agent")

    if request.data["target"] == "client":
        q = Agent.objects.filter(site__client_id=request.data["client"])
    elif request.data["target"] == "site":
        q = Agent.objects.filter(site_id=request.data["site"])
    elif request.data["target"] == "agents":
        q = Agent.objects.filter(pk__in=request.data["agentPKs"])
    elif request.data["target"] == "all":
        q = Agent.objects.all()
    else:
        return notify_error("Something went wrong")

    minions = [agent.salt_id for agent in q]
    agents = [agent.pk for agent in q]

    AuditLog.audit_bulk_action(request.user, request.data["mode"],
                               request.data)

    if request.data["mode"] == "command":
        handle_bulk_command_task.delay(agents, request.data["cmd"],
                                       request.data["shell"],
                                       request.data["timeout"])
        return Response(f"Command will now be run on {len(agents)} agents")

    elif request.data["mode"] == "script":
        script = get_object_or_404(Script, pk=request.data["scriptPK"])
        handle_bulk_script_task.delay(script.pk, agents, request.data["args"],
                                      request.data["timeout"])
        return Response(
            f"{script.name} will now be run on {len(agents)} agents")

    elif request.data["mode"] == "install":
        r = Agent.salt_batch_async(minions=minions,
                                   func="win_agent.install_updates")
        if r == "timeout":
            return notify_error("Salt API not running")
        return Response(
            f"Pending updates will now be installed on {len(agents)} agents")
    elif request.data["mode"] == "scan":
        bulk_check_for_updates_task.delay(minions=minions)
        return Response(
            f"Patch status scan will now run on {len(agents)} agents")

    return notify_error("Something went wrong")
예제 #9
0
def run_script(request):
    agent = get_object_or_404(Agent, pk=request.data["pk"])
    if not agent.has_nats:
        return notify_error("Requires agent version 1.1.0 or greater")
    script = get_object_or_404(Script, pk=request.data["scriptPK"])
    output = request.data["output"]
    req_timeout = int(request.data["timeout"]) + 3

    AuditLog.audit_script_run(
        username=request.user.username,
        hostname=agent.hostname,
        script=script.name,
    )

    data = {
        "func": "runscript",
        "timeout": request.data["timeout"],
        "script_args": request.data["args"],
        "payload": {
            "code": script.code,
            "shell": script.shell,
        },
    }

    if output == "wait":
        r = asyncio.run(agent.nats_cmd(data, timeout=req_timeout))
        return Response(r)
    elif output == "email":
        if not pyver.parse(agent.version) >= pyver.parse("1.1.12"):
            return notify_error("Requires agent version 1.1.12 or greater")

        emails = (
            [] if request.data["emailmode"] == "default" else request.data["emails"]
        )
        run_script_email_results_task.delay(
            agentpk=agent.pk,
            scriptpk=script.pk,
            nats_timeout=req_timeout,
            nats_data=data,
            emails=emails,
        )
        return Response(f"{script.name} will now be run on {agent.hostname}")
    else:
        asyncio.run(agent.nats_cmd(data, wait=False))
        return Response(f"{script.name} will now be run on {agent.hostname}")
예제 #10
0
    def post(self, request, format=None):

        # check credentials
        serializer = AuthTokenSerializer(data=request.data)
        if not serializer.is_valid():
            AuditLog.audit_user_failed_login(request.data["username"])
            return Response("bad credentials", status=status.HTTP_400_BAD_REQUEST)

        user = serializer.validated_data["user"]

        # if totp token not set modify response to notify frontend
        if not user.totp_key:
            login(request, user)
            response = super(CheckCreds, self).post(request, format=None)
            response.data["totp"] = "totp not set"
            return response

        return Response("ok")
예제 #11
0
    def post(self, request, format=None):
        valid = False

        serializer = AuthTokenSerializer(data=request.data)
        serializer.is_valid(raise_exception=True)
        user = serializer.validated_data["user"]

        token = request.data["twofactor"]
        totp = pyotp.TOTP(user.totp_key)

        if settings.DEBUG and token == "sekret":
            valid = True
        elif totp.verify(token, valid_window=1):
            valid = True

        if valid:
            login(request, user)
            AuditLog.audit_user_login_successful(request.data["username"])
            return super(LoginView, self).post(request, format=None)
        else:
            AuditLog.audit_user_failed_twofactor(request.data["username"])
            return Response("bad credentials", status=status.HTTP_400_BAD_REQUEST)