|
@@ -26,14 +26,15 @@ def args_read(l_search_parameter):
|
|
|
l_args = sys.argv[1:]
|
|
|
|
|
|
try:
|
|
|
- opts, args = getopt.getopt(l_args,"u:p:s:l:m:",["users=",
|
|
|
+ opts, args = getopt.getopt(l_args,"u:p:s:l:m:U;",["users=",
|
|
|
"products=",
|
|
|
"server=",
|
|
|
"ll=",
|
|
|
"mode=",
|
|
|
"csv=",
|
|
|
"domass=",
|
|
|
- "noimage=",
|
|
|
+ "noimage=",
|
|
|
+ "ini_file=",
|
|
|
])
|
|
|
except getopt.GetoptError as err_det:
|
|
|
print ("Error in reading parameters:" + str(err_det))
|
|
@@ -43,7 +44,10 @@ def args_read(l_search_parameter):
|
|
|
for opt, arg in opts:
|
|
|
if l_search_parameter == opt: #in ("-u", "--usage"):
|
|
|
return arg
|
|
|
- return None
|
|
|
+ # maybe there is something in ini-file:
|
|
|
+ if not l_search_parameter == "--ini_file":
|
|
|
+ return g_api_ini.get_parameter(l_search_parameter)
|
|
|
+ #return None
|
|
|
|
|
|
def print_args():
|
|
|
print("""
|
|
@@ -67,6 +71,8 @@ Call: python api_calls.py --parameters
|
|
|
When this is set, it will be between 1 and 3 recycling entries
|
|
|
--noimage=yes : If set to "yes" and mode=allnew, no images will be uploaded. Otherwise
|
|
|
test2.jpg will be uploaded for each new product
|
|
|
+ --ini_file= Path and name of INI-File to use (other command line arguments will overwrite
|
|
|
+ the settings from INI-File.
|
|
|
|
|
|
Suggested for standard use:
|
|
|
python api_calls.py --users=50 --products=1000
|
|
@@ -163,11 +169,24 @@ def g_check_status(resp):
|
|
|
return True
|
|
|
|
|
|
def g_get_header(i=9999999):
|
|
|
+ import time
|
|
|
|
|
|
l_token_key = g_users.get_user_and_login(i)
|
|
|
if not l_token_key:
|
|
|
- logger.critical("Token for user not recevied: " + str(i))
|
|
|
- raise SystemExit()
|
|
|
+ # Problem on 22.6. - Token_key would take ages until we can login with it.
|
|
|
+ for n in range(1,10):
|
|
|
+ logger.warn("Login not successfull - waiting 3 seconds " + str(i))
|
|
|
+ time.sleep( 3 )
|
|
|
+ for x in range(1,20):
|
|
|
+ l_token_key = g_users.get_user_and_login(i)
|
|
|
+ if l_token_key:
|
|
|
+ break
|
|
|
+ if l_token_key:
|
|
|
+ break
|
|
|
+
|
|
|
+ if not l_token_key:
|
|
|
+ logger.critical("Token for user not received: " + str(i))
|
|
|
+ raise SystemExit()
|
|
|
|
|
|
headers={'x-geolocation-header': "1:1",
|
|
|
"authorization": "Token " + l_token_key,
|
|
@@ -176,12 +195,50 @@ def g_get_header(i=9999999):
|
|
|
|
|
|
return headers
|
|
|
|
|
|
+class ini_contents:
|
|
|
+ def __init__(self, l_file=None):
|
|
|
+ #print ("Init im ini_contents aufgetreten. Usage ist:" + usage)
|
|
|
+ #traceback.print_stack()
|
|
|
+ if l_file is None:
|
|
|
+ self.__file = "init.ini" #"prod" or "test"
|
|
|
+ else:
|
|
|
+ self.__file = l_file
|
|
|
+ self.__attribs = {}
|
|
|
+ self.__open_ini()
|
|
|
+# self.__util = util()
|
|
|
+# self.__util.traceback()
|
|
|
+ def __open_ini(self):
|
|
|
+ self.__attribs["INI_FILE"] = self.__file
|
|
|
+ l_filename = self.__file
|
|
|
+
|
|
|
+ with (open(os.path.join(os.getcwd(), l_filename), "r")) as l_file:
|
|
|
+ for l_line in l_file.readlines():
|
|
|
+ # Kommentare ignorieren:
|
|
|
+ if len(l_line.strip()) == 0:
|
|
|
+ continue
|
|
|
+ if l_line[0] != "#":
|
|
|
+ l_line = l_line.strip()
|
|
|
+ self.__attribs[l_line.split("=")[0]] = l_line.split("=")[1]
|
|
|
+ if "ll" in self.__attribs:
|
|
|
+ self.__attribs["ll"] = get_proper_loglevel(self.__attribs["ll"])
|
|
|
+ else:
|
|
|
+ self.__attribs["ll"] = get_proper_loglevel("INFO")
|
|
|
+
|
|
|
+ def get_value(self, key_for_value):
|
|
|
+ if key_for_value[0:2] == "--":
|
|
|
+ key_for_value = key_for_value[2:]
|
|
|
+ if key_for_value in self.__attribs.keys():
|
|
|
+ return (self.__attribs[key_for_value])
|
|
|
+ else:
|
|
|
+ return None
|
|
|
class api_init:
|
|
|
- def __init__(self, min_number, iteration):
|
|
|
+ def __init__(self):
|
|
|
+ # Read the ini-file
|
|
|
+ self.ini_file = ini_contents(l_file=args_read("--ini_file"))
|
|
|
+ def set_default(self, min_number, iteration):
|
|
|
self.min_number = min_number
|
|
|
self.max_number = min_number + iteration
|
|
|
# BaseURL for API-Calls
|
|
|
- # Muss spaeter noch ersetzt werden - irgendwie aus INI-File ziehen oda so.
|
|
|
self.base_url = args_read("--server")
|
|
|
if not self.base_url:
|
|
|
self.base_url = "https://app-test.earthsquad.global/api"
|
|
@@ -190,6 +247,7 @@ class api_init:
|
|
|
l_datetime = datetime.now()
|
|
|
self.base = str(l_datetime.month + l_datetime.day) + str(l_datetime.hour + l_datetime.minute) + str(l_datetime.second)
|
|
|
logger.debug("Base-String: " + self.base)
|
|
|
+
|
|
|
def set_base_url(self, base_url):
|
|
|
self.base_url = base_url
|
|
|
def get_min_number(self):
|
|
@@ -200,6 +258,8 @@ class api_init:
|
|
|
return self.base_url
|
|
|
def get_base(self):
|
|
|
return self.base
|
|
|
+ def get_parameter(self, l_search_term):
|
|
|
+ return self.ini_file.get_value(l_search_term)
|
|
|
def get_g_mode(self):
|
|
|
l_gmode = args_read("--mode")
|
|
|
if not l_gmode:
|
|
@@ -266,7 +326,7 @@ class api_user:
|
|
|
self.l_counter = 1
|
|
|
self.l_token_key = self._login_(l_i)
|
|
|
return self.l_token_key
|
|
|
- elif self.l_counter > 50:
|
|
|
+ elif self.l_counter > 20:
|
|
|
self.l_counter = 0
|
|
|
return self.l_token_key
|
|
|
else:
|
|
@@ -315,9 +375,10 @@ class api_user:
|
|
|
l_reader = csv.reader(l_csvfile)
|
|
|
for l_row in l_reader:
|
|
|
# Testusers call start with a number and E-Mail @test.com
|
|
|
- if "test.com" in l_row[0] and l_row[0][0:1].isdigit():
|
|
|
- self.l_users.append([l_row[0].split("@test.com")[0], ""])
|
|
|
- l_i += 1
|
|
|
+ if len(l_row) >= 1:
|
|
|
+ if "test.com" in l_row[0] and l_row[0][0:1].isdigit():
|
|
|
+ self.l_users.append([l_row[0].split("@test.com")[0], ""])
|
|
|
+ l_i += 1
|
|
|
logger.info("File with Users Imported")
|
|
|
logger.info("Imported: " + str(l_i) + " users from CSV-File " + l_csv)
|
|
|
# If there were more users selected in the start-parameters (or automatically)
|
|
@@ -326,6 +387,21 @@ class api_user:
|
|
|
self.l_max_number = self.l_min_number + l_i
|
|
|
return l_i
|
|
|
|
|
|
+def g_recyclemat_random():
|
|
|
+ l_random = 0
|
|
|
+ l_rand_str_list = g_api_ini.get_parameter("recycle_producttypes")
|
|
|
+ if l_rand_str_list:
|
|
|
+ logger.debug("Using List for recycling material: " + l_rand_str_list)
|
|
|
+ l_rand_list = l_rand_str_list.split(";")
|
|
|
+ l_rand_pos = g_random(0,len(l_rand_list)-1)
|
|
|
+ logger.debug("Took position " + str(l_rand_pos) + " of list for this BOM or Bulk-Recycling-Item")
|
|
|
+ return l_rand_list[l_rand_pos]
|
|
|
+ else:
|
|
|
+ logger.debug("Not using standard product type")
|
|
|
+ l_random = g_random(3,17)
|
|
|
+
|
|
|
+ return l_random
|
|
|
+
|
|
|
class api_product_full:
|
|
|
def __init__(self, l_number, api_init):
|
|
|
# uses the EAN-Code and the product API
|
|
@@ -346,13 +422,18 @@ class api_product_full:
|
|
|
l_product = api_product(self.number, api_init=self.api_init)
|
|
|
self.product_id = l_product.create(self.ean_id)
|
|
|
|
|
|
+ # If product, that was created is not using a default producttype, create a BOM
|
|
|
+ if l_product.get_is_default() == 0:
|
|
|
# Create 1 to 4 BOM-Items for this product
|
|
|
- for l_bom in range(0, g_random(1,4)):
|
|
|
- # chose a random packaging material type
|
|
|
- api_bom(self.api_init, self.product_id, g_random(3,17), g_random(10,1000))
|
|
|
+ for l_bom in range(0, g_random(1,4)):
|
|
|
+ # chose a random packaging material type
|
|
|
+ api_bom(self.api_init, self.product_id, g_recyclemat_random(), g_random(10,1000))
|
|
|
|
|
|
# Upload Image_
|
|
|
- f_image_upload("test.jpg", self.product_id)
|
|
|
+ l_image = g_api_ini.get_parameter("image")
|
|
|
+ if not l_image:
|
|
|
+ l_image = "test2.jpg"
|
|
|
+ f_image_upload(l_image, self.product_id, l_image)
|
|
|
|
|
|
def read_server(self, id):
|
|
|
# Checks with this ID, whether a product exists @ server
|
|
@@ -462,8 +543,27 @@ class api_product:
|
|
|
self.number = l_number
|
|
|
self.l_api_init = api_init
|
|
|
self.l_base_url = self.l_api_init.get_base_url()
|
|
|
- self.l_base = self.l_api_init.get_base()
|
|
|
+ self.l_base = self.l_api_init.get_base()
|
|
|
+ self.l_uses_default_product = 0
|
|
|
def create(self, l_barcode_id):
|
|
|
+
|
|
|
+ # Randomly create products with and without default product_type
|
|
|
+ l_use_def_product = g_random(0,1)
|
|
|
+ if l_use_def_product == 1:
|
|
|
+ # Find the products, we're supposed to use from INI-File
|
|
|
+ l_def_products_in = g_api_ini.get_parameter("default_products")
|
|
|
+ if l_def_products_in:
|
|
|
+ # Identifiy the Standard product types we can use.
|
|
|
+ l_def_products = l_def_products_in.split(";")
|
|
|
+ # Get a random number within the array
|
|
|
+ l_use_product_position = g_random(0, len(l_def_products)-1)
|
|
|
+ # get the ID of this random number:
|
|
|
+ l_use_product = l_def_products[l_use_product_position]
|
|
|
+ self.l_uses_default_product = 1
|
|
|
+ logger.info("Using default product_type: " + str(l_use_product) + " for product " + self.l_base + str(self.number))
|
|
|
+ else:
|
|
|
+ l_use_product = 1
|
|
|
+
|
|
|
g_timeit.start("products")
|
|
|
url = self.l_base_url + "/scanapp/en-us/products/"
|
|
|
product_data = {
|
|
@@ -475,7 +575,7 @@ class api_product:
|
|
|
"height": 0,
|
|
|
"is_generic": "false",
|
|
|
"deleted": "false",
|
|
|
- "product_type": 1,
|
|
|
+ "product_type": l_use_product,
|
|
|
"weight_unit": 2
|
|
|
}
|
|
|
resp = g_post(url, headers=g_get_header(), json=product_data)
|
|
@@ -485,7 +585,9 @@ class api_product:
|
|
|
l_answer = resp.json()
|
|
|
logger.debug("Product: " + str(self.number) + " " + str(l_answer))
|
|
|
#x_result[i].append(l_answer["id"])
|
|
|
- return l_answer["id"]
|
|
|
+ return l_answer["id"]
|
|
|
+ def get_is_default(self):
|
|
|
+ return self.l_uses_default_product
|
|
|
|
|
|
def g_random(l_min, l_max):
|
|
|
return randint(l_min, l_max)
|
|
@@ -698,14 +800,13 @@ def f_daily_recycle():
|
|
|
while l_found_mat <= l_count_materials:
|
|
|
# Brute-force getting material-IDs from database
|
|
|
|
|
|
-
|
|
|
l_iterator = l_iterator + g_random(1, l_base_random)
|
|
|
l_product = api_product_full(l_iterator, g_api_ini)
|
|
|
l_ok_product = l_product.read_server(l_iterator)
|
|
|
- if l_endless_loop_counter >= 5:
|
|
|
+ if l_endless_loop_counter >= 25:
|
|
|
logger.error("Endless loop when trying to find materials. Exiting")
|
|
|
raise SystemExit()
|
|
|
- if l_not_found_counter >= 5:
|
|
|
+ if l_not_found_counter >= 7:
|
|
|
# If we didn't find a product after 5 tries
|
|
|
# we should reset the iterator.
|
|
|
l_iterator = 1
|
|
@@ -734,7 +835,7 @@ def f_daily_recycle():
|
|
|
l_product.recycle()
|
|
|
logger.info("Recycled " + str(l_product.get_id()) + " for user " + str(i))
|
|
|
|
|
|
-def f_image_upload(img_file, l_id):
|
|
|
+def f_image_upload(img_file, l_id, l_img_name="testimage"):
|
|
|
if args_read("--noimage") == "yes":
|
|
|
return None
|
|
|
|
|
@@ -750,7 +851,7 @@ def f_image_upload(img_file, l_id):
|
|
|
|
|
|
l_upload = {
|
|
|
"product" : str(l_id),
|
|
|
- "name" : "test2.jpg"
|
|
|
+ "name" : l_img_name
|
|
|
}
|
|
|
#g_timeit.end()
|
|
|
|
|
@@ -776,7 +877,7 @@ def f_bulk_recycling():
|
|
|
logger.info("Bulk recycling - items: " + str(i))
|
|
|
g_api_statistics.get_statistics(g_random(1,2), g_random(1,3))
|
|
|
g_timeit.start("bulk_recycling")
|
|
|
- recycle_data = {"product_type" : g_random(3,17), "weight" : g_random(100,1000), "weight_unit" : g_random(1,2)}
|
|
|
+ recycle_data = {"product_type" : g_recyclemat_random(), "weight" : g_random(100,1000), "weight_unit" : g_random(1,2)}
|
|
|
resp = g_post(url, headers=g_get_header(), json=recycle_data)
|
|
|
|
|
|
if g_check_status(resp):
|
|
@@ -800,10 +901,13 @@ def f_products_import():
|
|
|
|
|
|
print_args() #Prints the instructions how to start the program
|
|
|
|
|
|
+g_api_ini = api_init() #initizalize API
|
|
|
+
|
|
|
logger = g_logging_init()
|
|
|
|
|
|
l_iteration = f_products_import() #from command line parameter or default value
|
|
|
-g_api_ini = api_init(min_number=1000, iteration=l_iteration) #initizalize API
|
|
|
+g_api_ini.set_default(min_number=1000, iteration=l_iteration)
|
|
|
+
|
|
|
g_mode = g_api_ini.get_g_mode() #from command line parameter or default value
|
|
|
l_users = g_api_ini.get_l_users() #from command line parameter or default value
|
|
|
g_timeit = gc_timeit(g_api_ini) #Instanziate timer class
|
|
@@ -830,4 +934,5 @@ f_bulk_recycling()
|
|
|
|
|
|
g_timeit.printreport()
|
|
|
#g_perf_trace.perf_trace_end()
|
|
|
-print("\nall done - Thanks")
|
|
|
+print("\nall done - Thanks")
|
|
|
+
|