Performance testing framework–python+locust (2) use and error handling, port occupation handling when restarting the runtime

Directory

basic use

Error handling

port occupied


Basic use

import os
from locust import TaskSet, task, HttpUser, between, tag
from pprint import pprint
from load_data import get_data, user_mames, jqbh


class Test(TaskSet): # create task class
    def on_start(self): # initialization
        self. login()

    def login(self):
        self. headers = {
            "user-agent": "Dart/2.16 (dart:io)",
            "content-type": "application/json; charset=utf-8",
            "accept-encoding": "gzip",
            "content-length": "64",
            "host": "xxxxx"}
        json = {
            "username": get_data(user_mames),
            "password": "xxxxxx"
        }
        req = self.client.post('/user/oauth2/password', headers=self.headers, json=json, name='login')
        self.user_token = req.json()['result']['jwt_token']
        # pprint(req.json()['result']['jwt_token']) # print user token
        self.headers["jwt-token"] = self.user_token # add token to request header

    @tag('test1', 'test2') # set the label
    @task(1) # The number in @task(1) represents the weight of the task, and the larger the value, the higher the frequency of execution
    def get_UserInfo(self):
        userdata = self.client.get('/user/getUserInfo', headers=self.headers, name='get user information')
        # pprint(userdata.json()) # Print user information data

    @tag('test2')
    @task(10)
    def get_AlarmList(self):
        json = {
            "pageNo": 0,
            "pageSize": 20,
            "mark": [],
        }
        AlarmList_data = self.client.post('/alarm/getAlarmList', headers=self.headers, json=json, name='query jq list')
        pprint(AlarmList_data.json())

    @task # When the weight is not set, the default is 1
    def get_AlarmBookList(self):
        json = {
            "jqbh": "20230301155826A",
            "pageSize": 20
        }
        AlarmBookList_data = self.client.post('/alarmBook/getAlarmBookList', headers=self.headers, json=json,
                                              name='query jqws list')
        pprint(AlarmBookList_data.json())

    def on_stop(self): # Clear initialization, equivalent to teardown
        print('initialization clear')


class BI(HttpUser): # create user class
    # wait_time = between(3.0, 8.0) # Set the interval time during the running process, you need to introduce between in locust
    tasks = [Test]
    min_wait = 1000 # min_wait: The lower bound of user waiting time between execution transactions (unit: milliseconds)
    max_wait = 5000 # The upper bound of user waiting time between execution transactions (unit: milliseconds)
    host = 'xxxx'

if __name__ == '__main__':
    os.system('locust -f main.py --tag test2')

Part of the function description:

  • Weight setting: The @task decorator is added to the front of the defined method to indicate that this method is an executable task, and a number (@task(2)) can be added to the decoration method to indicate the proportion of execution times of the task (ie weight).
  • Response assertion: Adding an assertion to the request must set the catch_response parameter in the request method, the value is True, and the response assertion is as follows
 with self.client.get('/', catch_response = True) as response:
            if response.status_code == 200:
                response. success()
            else:
                response. failure('Failed!')
  • Waiting time: wait_time = between(5, 9), using the between function, the time can be randomly selected between the specified maximum and minimum values.
  • Tag filtering: during execution, the corresponding interface can be executed or not executed by specifying the first closed tag (select the tag [–tag], the interface to be executed after the parameter, separate multiple tags with spaces; exclude tags [ –exclude-tags], the tag-related interface after the parameter will not be executed, others will be executed)

Error Reporting

The request protocol is missing and an error is reported

Error message:

File “D:\python\lib\site-packages\requests\sessions.py”, line 792, in get_adapter
raise InvalidSchema(f”No connection adapters were found for {url!r}”)
requests.exceptions.InvalidSchema: No connection adapters were found for ‘117.57.107.86:48800/police-app/app-server/’

Processing method:

url = “127.0.0.1:xxxx”, you can add http:// or https:// before the requested address

Interface access error reporting

Error message:

{‘code’: ‘-1’, ‘message’: “Content type ‘application/x-www-form-urlencoded;charset=UTF-8’ not supported”, ‘ status’: 400, ‘timeElapsed’: 1, ‘timestamp’: 1676265488186}

Processing method:

Whether it is a POST request or a GET request, parameters can be successfully obtained in this way, but if the body in the front-end POST request is a Json object, the above error will be reported, and the parameter name needs to be specified before the request parameter.

# Before reporting an error:
        req = self.client.post('/user/oauth2/password',
                               {"username": "br", "password": "NO8tDZXEhvpiMYcI47amQA=="})

# After processing:
        req = self.client.post('/user/oauth2/password',
                              json = {"username": "br", "password": "NO8tDZXEhvpiMYcI47amQA=="})

Content-Type type error

Knowledge points – three common formats of Content-Type:

  • Content-Type: application/json, if there is no special statement, appiationl/son is the default Content-type of Asios, and it is also my most commonly used one. It declares that the data in the request body will be sent to in the form of json string rear end.
  • Content-Type: application/x-www-form-urlencoded, which declares that the data in the request body will be sent to the backend as a key-value pair (in the form of a normal form). This type is the default for Ajax.
  • Content-Type: multipart/form-data, generally used to upload files, specifying that the transmitted data is binary data, or in the form of key-value pairs.

Error message:

“Content type ‘application/x-www-form-urlencoded;charset=UTF-8’ not supported”

Reasons and solutions:

The reason for this problem is that the json data type does not conform to the front-end and back-end data interaction
json is divided into two types;
(1) JSON object type, that is, the Content type defined by the front end is application/x-www-form-urlencoded, etc.
(2) JSON string type, that is, the Content type defined by the front end is application/json
Solution
The json data type transmitted by the front end and the annotation used by the back end should have a correct correspondence

Port occupation

Windows query and clear occupied ports

Query all running ports: netstat -ano

[Hint: ‘netstat’ is not recognized as an internal or external command, operable program. Solution: Add path(;%SystemRoot%\system32) to the environment variable]

View process by pid: tasklist | findstr pid

View the occupied port pid: netstat -aon |findstr “8089”

Kill the specified pid process: taskkill -t -f /pid pid number

taskkill is the command to terminate the “process” of the specified program in the Windows command line:
Parameters: /f means force termination
/im indicates the specified process name, such as “explor.exe”, for example: taskkill /f /im java.exe
/pid indicates the specified process ID process number, example: taskkill /f /pid 7176