про оптимизируй код 

from pyzbar.pyzbar import ZBarSymbol
import cv2
import numpy as np

from qreader import QReader
from dbr import *

reader = BarcodeReader()
dbrerror = reader.init_license("t0073oQAAAEAwJrLq5VzRcOIb0TjKivFRNJiYQOSps7Vw2PLh4NaVXJc7uSsF7bGXePzhb6ZQQT/c1CMMHqep3bnNfhF3IxsXMikjpw==")

UPLOAD_FOLDER = 'uploads'
app = Flask(__name__)
app.config['UPLOAD_FOLDER'] = UPLOAD_FOLDER

qreader = QReader(model_size = 'n')

def compute_average_image_color(img):
    width, height = img.size

    r_total = 0
    g_total = 0
    b_total = 0

    count = 0
    for x in range(0, width):
        for y in range(0, height):
            r, g, b = img.getpixel((x,y))
            r_total += r
            g_total += g
            b_total += b
            count += 1

    return (r_total/count, g_total/count, b_total/count)

def compute_average_image_color_final(img):
    width, height = img.size

    r_total = 0
    g_total = 0
    b_total = 0

    count = 0
    for x in range(0, width):
        for y in range(0, height):
            r, g, b = img.getpixel((x,y))
            r_total += r
            g_total += g
            b_total += b
            count += 1

    return (((r_total/count)+(g_total/count)+(b_total/count))/3)

def makePdf(pdfFileName, listPages, dir = ''):
    if (dir):
        dir += "/"

    im = Image.open(dir + str(listPages[0]))
    if not im.mode == 'RGB':
        im = im.convert('RGB')
    im_list = []
    for page in listPages[1:]:
        im0 = Image.open(dir + str(page))
        if not im0.mode == 'RGB':
            im0 = im0.convert('RGB')
        im_list.append(im0)

    #print(dir + pdfFileName + ".pdf")
    im.save(dir + pdfFileName + ".pdf", "PDF", resolution=100.0, save_all=True, append_images=im_list,quality=20)

def write_bytesio_to_file(filename, bytesio):
    with open(os.path.join(app.config['UPLOAD_FOLDER'], filename), "wb") as outfile:
        outfile.write(bytesio.getbuffer())

def read_bytesio_from_file(filename):
    return io.open(app.config['UPLOAD_FOLDER'] + "/" + filename, "rb").read()



@app.route('/qr2', methods=['POST'])
def index2():
    start_time = time.monotonic()

    try:
        payload = request.get_json()
        path = ""
        filename = str(uuid.uuid4())+".png"
        if 'path' in payload:
            path = payload['path']
            urllib.request.urlretrieve(path, filename)
            img = Image.open(filename)
        else:
            image_stream = BytesIO(base64.b64decode(payload['data']))
            img = Image.open(image_stream)

        if not img.mode == 'RGB':
            img = img.convert('RGB')

        WhitePage = img.resize((50, 50))
        average_color = compute_average_image_color_final(WhitePage)
        average_color0 = compute_average_image_color(WhitePage)
        if average_color >= 254:
            return json.dumps({
                "status": "ok",
                "average_color": average_color,
                "average_color_data": average_color0,
                "WhitePage": bool(1),
                "FoundCode": bool(0),
                "dbrLic": dbrerror[1],
                "data": []
            })

        # Load an image to cv2
        frame = np.array(img)
        image = cv2.cvtColor(frame, cv2.COLOR_BGR2RGB)

        # Добавление белых границ (бордюр)
        image = cv2.copyMakeBorder(
            image,
            top=5,
            bottom=5,
            left=5,
            right=5,
            borderType=cv2.BORDER_CONSTANT,
            value=[255, 255, 255]  # Белый цвет бордюра
        )

        FoundCode = False
        elements = list()

        start_time = time.monotonic()
        text_results = reader.decode_buffer(image)
        elapsed_ms = (time.monotonic() - start_time) * 1000
        print("dbr time: "+str(elapsed_ms))
        if text_results != None:
            for text_result in text_results:
                if text_result.barcode_format_string == 'QR_CODE':
                    FoundCode = True
                    print("dbr -> "+str(text_result.barcode_text))
                    if text_result.barcode_text.find("**") == -1 and text_result.barcode_text.find("BarcodeBytes") == -1:
                        elements.append({
                            "data": text_result.barcode_text,
                            "type": text_result.barcode_format_string,
                            "lib": "dbr",
                            "time": int(elapsed_ms)
                        })
        print("----------------------")

        # OpenCV2 статический поиск QR + Обработка из либы QReader
        NoCode = True
        clone = image.copy()

        # Нормализация изображений и выделение черного канала (K-channel)
        imgFloat = clone.astype(np.float64) / 255.
        kChannel = 1 - np.max(imgFloat, axis=2)
        kChannel = (255 * kChannel).astype(np.uint8)

        # Бинаризация для выделения областей интереса
        _, thresh = cv2.threshold(kChannel, 190, 255, cv2.THRESH_BINARY)

        # Применение морфологических операций
        kernel = cv2.getStructuringElement(cv2.MORPH_RECT, (5,5))
        close = cv2.morphologyEx(thresh, cv2.MORPH_CLOSE, kernel, iterations=2)

        # Поиск контуров
        cnts = cv2.findContours(close, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
        cnts = cnts[0] if len(cnts) == 2 else cnts[1]

        # Обработка каждого контура
        for c in cnts:
            peri = cv2.arcLength(c, True)
            approx = cv2.approxPolyDP(c, 0.04 * peri, True)
            x,y,w,h = cv2.boundingRect(approx)
            area = cv2.contourArea(c)
            ar = w / float(h)
            if len(approx) == 4 and area > 9000 and ar < 1.3:
                cropped_image = image[y-5:y+h+5, x-5:x+w+5]

                height, width, cannal = cropped_image.shape
                if height==0 or width==0:
                    continue

                quadrilateral_xy = np.array([[0, 0],[0, height],[width, height],[height, 0]])
                detection_result = qreader.get_detection_result_from_polygon(quadrilateral_xy)

                start_time = time.monotonic()
                output = qreader.decode(cropped_image, detection_result=detection_result)
                elapsed_ms = (time.monotonic() - start_time) * 1000
                print("OpenCV2 time: "+str(elapsed_ms))

                print("OpenCV2-> "+str(output))
                print("----------------------")
                if output != None:
                    FoundCode = True
                    NoCode = False
                    elements.append({
                        "data": output,
                        "type": "QRCODE",
                        "lib": "OpenCV2",
                        "time": int(elapsed_ms)
                    })
                    #break

        if NoCode == True:
            # QReader YOLOv8 Нейросеть
            start_time = time.monotonic()
            outputs = qreader.detect_and_decode(image=image)
            elapsed_ms = (time.monotonic() - start_time) * 1000
            print("YOLOv8 time: "+str(elapsed_ms))
            print("YOLOv8 -> "+str(outputs))
            print("----------------------")
            for output in outputs:
                if output != None:
                    FoundCode = True
                    elements.append({
                        "data": output,
                        "type": "QRCODE",
                        "lib": "YOLOv8",
                        "time": int(elapsed_ms)
                    })

        WhitePage = img.resize((50, 50))
        average_color = compute_average_image_color_final(WhitePage)
        average_color_data = compute_average_image_color(WhitePage)

        if os.path.isfile(filename):
            os.remove(filename)

        return json.dumps({
            "status": "ok",
            "average_color": average_color,
            "average_color_data": average_color_data,
            "WhitePage": bool(0),
            "FoundCode": FoundCode,
            "dbrLic": dbrerror[1],
            "data": elements
        })

    except Exception as e:
        return json.dumps({"status": "Internal error", "error": str(e)})


@app.route('/CreatePDF', methods=['POST','GET'])
def upload_file():
    try:
        if request.method == 'POST':
            im_list = []
            payload = request.get_json()
            for (k, v) in payload.items():
                #print("Key: " + k)
                im_list.append(k + v['Ext'])
                myio = BytesIO(base64.b64decode(v['Data']))
                write_bytesio_to_file(k + v['Ext'], myio)
                myio.close()
            filename = str(uuid.uuid4())
            makePdf(filename, im_list, app.config['UPLOAD_FOLDER'])
            upload_pdf = base64.b64encode(read_bytesio_from_file(filename +".pdf"))
            for (i) in im_list:
                os.remove(app.config['UPLOAD_FOLDER'] + "/" + i)
                #print(app.config['UPLOAD_FOLDER']+ "/" + i)
            os.remove(app.config['UPLOAD_FOLDER'] + "/" + filename +".pdf")
#            gc.collect()
            return json.dumps({
                "status": "ok",
                "data": upload_pdf.decode()
            })
        return json.dumps({"status": "Internal error"})
    except:
        return json.dumps({"status": "Internal error"})

if __name__ == "__main__":
    app.run()