Author Topic: Python script help needed.  (Read 12033 times)

TheRealUMaster

  • PGP
  • Posts: 45
Python script help needed.
« on: August 30, 2016, 02:33:18 AM »
Hello.

Me and hate are working on several server configs.

We would like to have a script wich gets the current/next map's name (e.g. airtime2) and triggers specific commands (eg. set gravity 233 or sv_consolename 2) based on wich map is the current/next one (for example if airtime3 is loaded as the current map, then set the consolename to 3 and set expert to 3 (just an example).
We also would like to have all the commands in a container form (e.g array) and then chosen from that container (e.g if airtimeoi then get the commands from the 3rd and the 6th line of the array/container).
We already did the part when the script sends some commands in rcon form to the server (for example the pgp script), but I got stuck at the part where a python script gets specific data from a running pb2 server instance, so I'd appreciate any help related to this issue (and some explanation IN the script in form of some comments too).

As always, have a nice day.

Cheers, UMaster.

ic3y

  • Committee Member
  • Autococker
  • Posts: 1396
Re: Python script help needed.
« Reply #1 on: August 30, 2016, 01:45:46 PM »
hTml will be here in a minute, please wait.

mRokita

  • Autococker
  • Posts: 598
Re: Python script help needed.
« Reply #2 on: August 30, 2016, 03:25:17 PM »
hTml will be here in a minute, please wait.
I don't check the forums very often nowadays, I do it once a month or something like this. The 'Python' word in the topic has captured my attention though.
You can use pypb2lib for this thing I think - https://github.com/mRokita/pypb2lib

mRokita

  • Autococker
  • Posts: 598
Re: Python script help needed.
« Reply #3 on: August 30, 2016, 03:31:22 PM »
Code: [Select]
>>> from pypb2lib import Server
>>> s = Server('rcon', '109.235.71.123', 30000)
>>> data = s.Status()
>>> data
{'gamename': 'Digital Paint Paintball 2 v1.930(186)', 'protocol': '34', 'elim': '13', '_scores': 'Blue:5 Red:0 ', 'pr': '!2!3!4!7!10', 'gamedir': 'pball', 'timelimit': '15', 'hostname': 'ygame pgp', 'pb': '!5!6!8!9', 'version': '2.00 i386 Aug 19 2015 Linux (41)', 'maxclients': '16', 'location': 'D\xfcsseldorf', 'po': '!0!1', 'needpass': '0', 'sv_login': '1', 'gamedate': 'Aug 19 2015', 'mapname': 'beta/kokain_b1', 'game': 'pball', 'sv_certificated': '0', 'fraglimit': '50', 'gameversion': 'DPPB2 v1.930(186)', 'TimeLeft': '14:46', 'players': [{'score': '0', 'ping': '36', 'name': 'Embla'}, {'score': '0', 'ping': '62', 'name': 'hate_you_guys'}, {'score': '0', 'ping': '85', 'name': '>og<Extrawelt'}, {'score': '0', 'ping': '0', 'name': '.avR|ZalMa'}, {'score': '1', 'ping': '75', 'name': 'naonamem'}, {'score': '2', 'ping': '61', 'name': 'Lofas'}, {'score': '0', 'ping': '144', 'name': 'USFYOBOB64'}, {'score': '0', 'ping': '95', 'name': 'NTFA'}, {'score': '1', 'ping': '168', 'name': 'crazylady'}, {'score': '0', 'ping': '56', 'name': 'planB'}, {'score': '0', 'ping': '158', 'name': 'eliminator.com'}]}
>>> data['mapname']
'beta/kokain_b1'
>>> s.rcon('map airtime') // Change current map to airtime
I apologize for the function naming, I know that it's not pep8 compatible... I didn't know that something like pep8 exists when I was writing it.

TheRealUMaster

  • PGP
  • Posts: 45
Re: Python script help needed.
« Reply #4 on: August 31, 2016, 02:24:32 AM »
I don't check the forums very often nowadays, I do it once a month or something like this. The 'Python' word in the topic has captured my attention though.
You can use pypb2lib for this thing I think - https://github.com/mRokita/pypb2lib
Ah, hTml, thank you very much :)

also, how can I use this in a "if" condition? (sorry for this stupid question but I am very new to python)

if(data['mapname'] == 'airtimeoi') { s.rcon('expert 8') } else { sleep 5 }

?

rockitude

  • Committee Member
  • 68 Carbine
  • Posts: 492
Re: Python script help needed.
« Reply #5 on: August 31, 2016, 04:32:46 AM »
if data["mapname"] == "airtimeoi":
    s.rcon("expert 8")
else:
    time.sleep(5)

This would be the correct syntax.

TheRealUMaster

  • PGP
  • Posts: 45
Re: Python script help needed.
« Reply #6 on: August 31, 2016, 05:28:04 AM »
Thank you very much. I appreciate your help :)

How do I tell the server to look up map name every x seconds?
Does the following script (wich I made based on your answers) CONSTANTLY and Repeatedly look at the server to see if airtimeoi, or airtime2 or airtime3 is the current map and triggerning ONLY the command for that specific map?

while True:
           s = Server('rcon', '109.235.71.123', 30000)
           data = s.Status()
           if data["mapname"] == "airtimeoi":
               s.rcon("expert 8")
           elif data["mapname"] == "airtime2":
               s.rcon("expert 1")
           elif data["mapname"] == "airtime3":
               s.rcon("expert 4")

« Last Edit: August 31, 2016, 05:59:43 AM by TheRealUMaster »

mRokita

  • Autococker
  • Posts: 598
Re: Python script help needed.
« Reply #7 on: August 31, 2016, 07:33:01 AM »
Thank you very much. I appreciate your help :)

How do I tell the server to look up map name every x seconds?
Does the following script (wich I made based on your answers) CONSTANTLY and Repeatedly look at the server to see if airtimeoi, or airtime2 or airtime3 is the current map and triggerning ONLY the command for that specific map?

while True:
           s = Server('rcon', '109.235.71.123', 30000)
           data = s.Status()
           if data["mapname"] == "airtimeoi":
               s.rcon("expert 8")
           elif data["mapname"] == "airtime2":
               s.rcon("expert 1")
           elif data["mapname"] == "airtime3":
               s.rcon("expert 4")


Yes it does.
The expert command applies expert mode to the next map so it won't work the way you expect it to work i think.
So I would use this solution instead:
Code: [Select]
import pypb2lib

def mapchange(data):
    # data['map'] == name of the loaded map
    s.rcon('expert 8') # Set expert mode for the next map
    s.rcon('map ' + data['map']) # Reload the map

if __name__ == '__main__':
    s = pypb2lib.Server(rcon_password='rcon_password', hostname='ip', port=27910,   logfile='path_to_servers_logfile.log')
    s.Bind(pypb2lib.EVT_MAPCHANGE, mapchange)
WARNING - THIS METHOD REQUIRES ACCESS TO THE LOGFILE
« Last Edit: August 31, 2016, 12:58:17 PM by mRokita »

mRokita

  • Autococker
  • Posts: 598

TheRealUMaster

  • PGP
  • Posts: 45
Re: Python script help needed.
« Reply #9 on: August 31, 2016, 08:06:05 AM »
Yes it does.
The expert command applies expert mode to the next map so it won't work the way you expect it to work i think.
So I would use this solution instead:
Code: [Select]
import pypb2lib

def mapchange(data):
    # data['map'] == name of the loaded map
    s.rcon('expert 8') # Set expert mode for the next map
    s.rcon('map ' + data['map']) # Reload the map

if __name__ == '__main__':
    s = Server(rcon_password='rcon_password', hostname='ip', port=27910,   logfile='path_to_servers_logfile.log')
    s.Bind(pypb2lib.EVT_MAPCHANGE, mapchange)
WARNING - THIS METHOD REQUIRES ACCESS TO THE LOGFILE
Ah thanks. expert 8 was just an example :)
I just wanted to check if my syntax is correct :D
So i just need to add those import lines to my (above-mentioned) script and it should work.. thx :)

EDIT: i doesnt work

My Script:
Code: [Select]
import pypb2lib
from pypb2lib import Server
while True:
s = Server('rcon', '109.235.71.123', 11111)
data = s.Status()
if data["mapname"] == "airtimeoi":
s.rcon("sv_consolename 4")
s.rcon("say TEST")
elif data["mapname"] == "airtime2":
s.rcon("sv_consolename 3")
s.rcon("say TEST")
elif data["mapname"] == "airtime3":
s.rcon("sv_consolename 1")
s.rcon("say TEST")

Command line:

Code: [Select]
umaster@23246:/paintball/umaster/pball/scripts$ python cvar_cpublic.py
  File "cvar_cpublic.py", line 7
    s.rcon("sv_consolename 4")
    ^
IndentationError: expected an indented block

rockitude

  • Committee Member
  • 68 Carbine
  • Posts: 492
Re: Python script help needed.
« Reply #10 on: August 31, 2016, 08:21:02 AM »
UMaster, you should google "Python indentation". Python uses it instead of brackets.

if data["mapname"] == "airtimeoi":
s.rcon("sv_consolename 4")

Should be:

if data["mapname"] == "airtimeoi":
    s.rcon("sv_consolename 4")

^--- 4 spaces


I would probably do it like this. I'm not sure if it works, but you should get the idea.

Code: [Select]
from pypb2lib import Server
import time

maplist = {
    "airtimeoi": "expert 8",
    "airtime2": "expert 1",
    "airtime3": "expert 4",
}

serv = Server("rcon", "109.235.71.123", 30000)
current_map = ""

while True:

    for newmap, expert in maplist.items():
        map_unchanged = True
        while map_unchanged:
            data = serv.Status()
            mapname = data["mapname"]
            if mapname != current_map:
                serv.rcon("nextmap " + newmap)
                serv.rcon(expert)
                current_map = mapname
                map_unchanged = False
            else:
                time.sleep(300)
« Last Edit: August 31, 2016, 09:34:28 AM by rockitude »

TheRealUMaster

  • PGP
  • Posts: 45
Re: Python script help needed.
« Reply #11 on: August 31, 2016, 09:01:02 AM »
UMaster, you should google "Python indentation". Python uses it instead of brackets.

if data["mapname"] == "airtimeoi":
s.rcon("sv_consolename 4")

Should be:

if data["mapname"] == "airtimeoi":
    s.rcon("sv_consolename 4")

^--- 4 spaces


I would probably do it like this. I'm not sure if it works, but you should get the idea.

Code: [Select]
code ...
Thank you, rockitude. Now I don't have any syntax errors now, but apart from lagging my running pb2 server crazy, the script does NOTHING.
Is a time.sleep(x) crucial? And will my script work?
As for your code, I understand what you have written there, but there are/would be 2 problems with your code.
1st: I dont need any command to be executed apart from what I have specified in a block/array.
2nd: I assume your script wouldn't work if I would tell it to execute 2 different (for example say "TEST" and sv_consolename 3) commands (probably because of your 'for' statement).

I feel that I need to apologise again for wasting your time on this script, but I have almost 0 python knowledge.
Here is the lastest, currently non-working version of my script:
Code: [Select]
import pypb2lib
from pypb2lib import Server
while True:
s = Server(', '109.235.71.123', 11111)
data = s.Status()
if data["mapname"] == "airtimeoi":
   s.rcon("sv_consolename 4")
   s.rcon("say TEST")
elif data["mapname"] == "airtime2":
   s.rcon("sv_consolename 3")
   s.rcon("say TEST")
elif data["mapname"] == "airtime3":
   s.rcon("sv_consolename 1")
   s.rcon("say TEST")
« Last Edit: August 31, 2016, 11:52:49 AM by TheRealUMaster »

rockitude

  • Committee Member
  • 68 Carbine
  • Posts: 492
Re: Python script help needed.
« Reply #12 on: August 31, 2016, 09:21:57 AM »
You need to change your rcon password, you posted it here.

Quote
2nd: I assume your script wouldn't work if I would tell it to execute 2 different (for example say "TEST" and sv_consolename 3) commands (probably because of your 'for' statement).

You could change the dictionary to something like this, but I would go with html's version. He is more fluent in Python and wrote the pypb2lib module that you want to use.

maplist = {
    "airtimeoi": ["expert 8", "say TEST"],
    "airtime2": ["expert 1", "say TEST"],
    "airtime3": ["expert 4", "say TEST"],
}


Edit: Yea I had a mistake in my script. Never compiled it.

current_map = newmap    -->   current_map = data["mapname"]

rockitude

  • Committee Member
  • 68 Carbine
  • Posts: 492
Re: Python script help needed.
« Reply #13 on: August 31, 2016, 10:17:05 AM »
I got the time and tested it by myself and can't get the rcon command for "nextmap" to work. Does it even exist?

Code: [Select]
from pypb2lib import Server
import time

maplist = {
    "airtimeoi": ["sv expert 8", "say TEST"],
    "airtime2": ["sv expert 1", "say TEST"],
    "airtime3": ["sv expert 4", "say TEST"],
}

serv = Server("", "185.44.107.127", 11111)
current_map = ""

while True:

    for newmap, commands in maplist.items():
        map_unchanged = True
        while map_unchanged:
            data = serv.Status()
            mapname = data["mapname"]
            if mapname != current_map:
                serv.rcon("sv nextmap " + newmap)
                for command in commands:
                    serv.rcon(command)
                current_map = mapname
                map_unchanged = False
            else:
                time.sleep(300)

TheRealUMaster

  • PGP
  • Posts: 45
Re: Python script help needed.
« Reply #14 on: August 31, 2016, 11:56:35 AM »
The rcon commad is "map". newmap works only ingame :)
Thanks for the help, I'll try to contact hTml personally.
Also, sorry that I dont have enough time to mention them all, but you still have errors in your script.

mRokita

  • Autococker
  • Posts: 598
Re: Python script help needed.
« Reply #15 on: August 31, 2016, 12:57:39 PM »
Oh my bad, replace Server with pypb2lib.Server and it will work.
(I wrote that script without running python :P )
I've just tested it on my VPS so i can confirm that it works.

TheRealUMaster

  • PGP
  • Posts: 45
Re: Python script help needed.
« Reply #16 on: August 31, 2016, 01:09:23 PM »
Oh my bad, replace Server with pypb2lib.Server and it will work.
(I wrote that script without running python :P )
I've just tested it on my VPS so i can confirm that it works.
You tested my code?
If not, can you send me the code you tested?
Also have you tested that it does the commands in paintball that you specified? Or just if the script doesnt return any errors?) see this:
Now I don't have any syntax errors now, but apart from lagging my running pb2 server crazy (script launched --> instant lag, later timeout ingame), the script does NOTHING.

mRokita

  • Autococker
  • Posts: 598
Re: Python script help needed.
« Reply #17 on: August 31, 2016, 02:04:59 PM »
I've tested my code and it executes the correct commands.
I mean this one:
Code: [Select]
import pypb2lib

def mapchange(data):
    # data['map'] == name of the loaded map
    s.rcon('expert 8') # Set expert mode for the next map
    s.rcon('map ' + data['map']) # Reload the map

if __name__ == '__main__':
    s = pypb2lib.Server(rcon_password='rcon_password', hostname='ip', port=27910,   logfile='path_to_servers_logfile.log')
« Last Edit: September 01, 2016, 12:33:04 AM by mRokita »

Squeeze

  • 68 Carbine
  • Posts: 406
Re: Python script help needed.
« Reply #18 on: September 01, 2016, 12:58:07 AM »
Kevin xD

ic3y

  • Committee Member
  • Autococker
  • Posts: 1396
Re: Python script help needed.
« Reply #19 on: October 08, 2016, 01:18:01 PM »
Thank you, rockitude. Now I don't have any syntax errors now, but apart from lagging my running pb2 server crazy, the script does NOTHING.

hTml's script doesnt work when you use "set timestamp_date 1", because the RegEx doesnt fit then.

Just saw it in a quick lookup.