Blockly
This commit is contained in:
Executable
+326
@@ -0,0 +1,326 @@
|
||||
import ast
|
||||
import datetime
|
||||
import json
|
||||
import re
|
||||
import uuid
|
||||
import logging
|
||||
import base64
|
||||
import subprocess
|
||||
import tempfile
|
||||
import easywebdav
|
||||
import os
|
||||
import os.path
|
||||
import requests
|
||||
import hashlib
|
||||
from PIL import Image,ImageDraw,ImageFont
|
||||
|
||||
from odoo import api, fields, models, _
|
||||
from odoo import tools
|
||||
from odoo.exceptions import ValidationError
|
||||
from datetime import date
|
||||
from datetime import datetime
|
||||
from dateutil.relativedelta import relativedelta
|
||||
from pyffmpeg import FFmpeg
|
||||
from tuya_iot import TuyaOpenAPI, TUYA_LOGGER
|
||||
from tuya_connector import TuyaOpenAPI, TUYA_LOGGER
|
||||
from webdav4.client import Client
|
||||
from webdav4.fsspec import WebdavFileSystem
|
||||
import sys
|
||||
|
||||
TUYA_LOGGER.setLevel(logging.DEBUG)
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
|
||||
class dsscsvs(models.Model):
|
||||
|
||||
@api.model
|
||||
def create(self,vals):
|
||||
result = super().create(vals)
|
||||
return result
|
||||
|
||||
_name = "dss.csvs"
|
||||
_description = "DigitalSignage CSV Dateien"
|
||||
# _inherit = ['mail.thread','mail.activity.mixin']
|
||||
_rec_name = "csv_id"
|
||||
# _inherit = ['mail.thread', 'mail.activity.mixin']
|
||||
|
||||
uuid = fields.Char(default=lambda self: self._default_uuid(), required=True, readonly=True, copy=False, string='UUID')
|
||||
date_create = fields.Date('Erstellungsdatum',default=lambda self: self._default_create_date())
|
||||
date_lastedit = fields.Date('Änderungsdatum')
|
||||
user_create = fields.Char('Erstellungsuser',default=lambda self: self._default_create_user())
|
||||
user_lastedit = fields.Char('Änderungsuser')
|
||||
csv_id = fields.Char(string="CSV ID", required=True, help = "Das ist eine eindeutige ID für diese Dateityp. Sie wird automatisch generiert und sollte nicht manuell geändert werden.", default=lambda self: self._default_csv_id())
|
||||
csv_name = fields.Char(string="CSV Name", required=True, help = "Der Name des Dateityp, die Sie hochladen möchten. Dieser Name wird in der Benutzeroberfläche angezeigt.")
|
||||
csv_binary = fields.Binary(string="CSV Datei", help = "Die eigentliche Datei, die Sie hochladen möchten. Diese Datei wird in der Datenbank und Cloud gespeichert")
|
||||
csv_filename = fields.Char(string="CSV Dateiname", help = "Der Name der hochgeladenen Datei. Dies wird automatisch aus dem Dateinamen der hochgeladenen Datei abgerufen.",compute="_compute_csv_filename", store=True)
|
||||
csv_cloud_link = fields.Char(string="Cloud Link", help = "Der Link zur Datei in der Cloud, wenn die Datei in der Cloud gespeichert ist.")
|
||||
csv_description = fields.Text(string="CSV Beschreibung", help = "Eine Beschreibung der hochgeladenen Datei. Dies kann Informationen über den Inhalt der Datei, den Verwendungszweck oder andere relevante Details enthalten.")
|
||||
csv_attachment_id = fields.Many2one('ir.attachment', string="CSV Anhang", help = "Der Anhang, der mit dieser CSV-Datei verbunden ist. Dieser Anhang enthält die tatsächliche Datei, die in der Datenbank gespeichert ist.")
|
||||
csv_mailtext = fields.Text(string="CSV Mailtext", help = "Der Text, der in der E-Mail verwendet wird, wenn diese CSV-Datei per E-Mail versendet wird.")
|
||||
|
||||
|
||||
|
||||
@api.depends('binary_binary')
|
||||
@api.onchange('binary_binary')
|
||||
def _compute_binary_filename(self):
|
||||
"""Compute the binary filename based on the uploaded file."""
|
||||
_logger.info("Binary getting Filename - B_"+str(self.id))
|
||||
if len(self)>0:
|
||||
for record in self:
|
||||
if record.binary_binary:
|
||||
# Extract the filename from the binary content
|
||||
extension = 'jpg' # Default extension
|
||||
if isinstance(self.binary_binary, str):
|
||||
filedata = base64.b64decode(self.binary_binary.split("base64,")[-1])
|
||||
else:
|
||||
filedata = base64.b64decode(self.binary_binary)
|
||||
filedataStr = str(filedata)
|
||||
_logger.info("Binary getting Filename - B_"+str(self.id)+" - ["+str(filedataStr[0:23])+"]")
|
||||
if filedataStr[0:12] == "b'\\x89PNG\\":
|
||||
extension = 'png'
|
||||
elif filedataStr[0:17] == "b'\\xff\\xd8\\xff":
|
||||
extension = 'jpg'
|
||||
elif filedataStr[0:8] == "b'GIF89a":
|
||||
extension = 'gif'
|
||||
elif filedataStr[0:22] == "b'\\x49\\x49\\x2a\\x00":
|
||||
extension = 'tif'
|
||||
elif filedataStr[0:27] == "b'\\x25\\x50\\x44\\x46\\x2d":
|
||||
extension = 'pdf'
|
||||
elif filedataStr[0:23] == "b'\\x00\\x00\\x00 ftypisom":
|
||||
extension = 'mp4'
|
||||
elif filedataStr[0:22] == "b'\\x00\\x00\\x00\\x18ftyp":
|
||||
extension = 'mp4'
|
||||
elif filedataStr[0:12] == "b'\\x42\\x4d":
|
||||
extension = 'bmp'
|
||||
record.binary_filename = f"{record.binary_mediatype.filepartname}{record.binary_contract.contract_auto_id}.{extension}"
|
||||
|
||||
@api.model
|
||||
def _default_uuid(self):
|
||||
return str(uuid.uuid4())
|
||||
|
||||
@api.model
|
||||
def _default_create_date(self):
|
||||
return datetime.now().strftime('%Y-%m-%d %H:%M:%S')
|
||||
|
||||
@api.model
|
||||
def _default_create_user(self):
|
||||
return self.env.user.name if self.env.user else 'System'
|
||||
|
||||
@api.model
|
||||
def _default_binary_id(self):
|
||||
# Generate a unique binary ID based on the current timestamp and a random UUID
|
||||
return f"Datei_{str(uuid.uuid4())[:8]}"
|
||||
|
||||
@api.onchange('binary_binary')
|
||||
def _onchange_binary_binary(self):
|
||||
"""Update binary size and type when binary content is changed."""
|
||||
_logger.info("New Binary B_"+str(self.id))
|
||||
existing_binary = False
|
||||
if not self._origin.binary_binary:
|
||||
existing_binary = False
|
||||
else:
|
||||
existing_binary = True
|
||||
|
||||
if not self.binary_contract.cloudlink:
|
||||
raise ValidationError(_("Der Vertrag hat keinen Cloudlink. Bitte überprüfen Sie den Vertrag."))
|
||||
cloudpath = str(self.binary_contract.cloudlink)
|
||||
_logger.info("New Binary checking Cloudlink B_"+str(self.id)+" - "+str(cloudpath))
|
||||
cloudpath = cloudpath + '/' + str(self.binary_mediatype.cloudlink)
|
||||
client = Client("https://cloud.logumedia.de/remote.php/dav/files/OdooDav/", auth=("odooClient@logumedia.de", "lm2020#OdooDav"))
|
||||
_logger.info("New Binary checking Cloudlink for cont : "+str(cloudpath))
|
||||
cloudexists = False
|
||||
if client.exists(cloudpath):
|
||||
# Convert self.binary_binary to bytes-like object
|
||||
if isinstance(self.binary_binary, str):
|
||||
filedata = base64.b64decode(self.binary_binary.split("base64,")[-1])
|
||||
else:
|
||||
filedata = base64.b64decode(self.binary_binary)
|
||||
filedataStr = str(filedata)
|
||||
_logger.info("New Binary Cloudlink exists - Saving File - B_"+str(self.id)+" - "+str(cloudpath)+" - " + str(filedata)+' - ' + filedataStr[0:8])
|
||||
try:
|
||||
decoded_data = filedata
|
||||
except base64.binascii.Error as e:
|
||||
if 'Incorrect padding' in str(e):
|
||||
filedataStr += b'=' * (4 - len(filedataStr) % 4)
|
||||
decoded_data = base64.b64decode(filedataStr)
|
||||
if filedataStr[0:10] == "b'\x89PNG":
|
||||
extension = 'png'
|
||||
else:
|
||||
extension = 'jpg'
|
||||
_logger.info("New Binary Cloudlink exists - Saving File - B_"+str(self.id)+" - "+str(cloudpath)+" - " + str(base64.b64encode(decoded_data)))
|
||||
##infile = open('/tmp/'+filename, "w+b")
|
||||
#infile = tempfile.NamedTemporaryFile(delete=False)
|
||||
##infile.write(filedata)
|
||||
##client.upload_fileobj(infile, f"{cloudpath}/{filename}")
|
||||
##infile.close()
|
||||
##infile.delete() # Delete the temporary file after upload
|
||||
cloudexists = True
|
||||
else:
|
||||
_logger.info("New Binary Cloudlink does not exists B_"+str(self.id)+" - "+str(cloudpath))
|
||||
raise ValidationError(_("Der Cloudlink im Vertrag ist nicht vorhanden. Bitte überprüfen Sie den Link ggf. anlegen."))
|
||||
|
||||
if cloudexists:
|
||||
if self.binary_binary:
|
||||
# Calculate the size of the binary content
|
||||
self.binary_size = len(filedata)
|
||||
# Determine the file type based on the binary content
|
||||
self.binary_cloud_link = f"{cloudpath}/{self.binary_filename}"
|
||||
self.binary_issaved = True
|
||||
else:
|
||||
self.binary_size = 0
|
||||
self.binary_type = ''
|
||||
self.binary_cloud_link = ''
|
||||
self.binary_issaved = False
|
||||
|
||||
|
||||
def dload(self):
|
||||
"""Download the binary file."""
|
||||
if not self.binary_binary:
|
||||
raise ValidationError(_("No binary file to download."))
|
||||
|
||||
# Create a temporary file to store the downloaded content
|
||||
temp_file = tempfile.NamedTemporaryFile(delete=False, suffix=self.binary_filename)
|
||||
temp_file.write(base64.b64decode(self.binary_binary))
|
||||
temp_file.close()
|
||||
|
||||
# Return the file for download
|
||||
return {
|
||||
'type': 'ir.actions.act_url',
|
||||
'url': f'/web/content/{self.id}/{self.binary_filename}?download=true&filename={self.binary_filename}',
|
||||
'target': 'self',
|
||||
}
|
||||
|
||||
def dedit(self):
|
||||
"""Edit the binary file."""
|
||||
return {
|
||||
'type': 'ir.actions.act_window',
|
||||
'res_model': 'dss.binaries',
|
||||
'view_mode': 'form',
|
||||
'res_id': self.id,
|
||||
'target': 'new',
|
||||
}
|
||||
|
||||
def resend(self):
|
||||
"""Resend the binary file to the contract's partner email."""
|
||||
if not self.binary_contract:
|
||||
raise ValidationError(_("No contract associated with this binary file."))
|
||||
if not self.binary_contract.project.standortpartner:
|
||||
raise ValidationError(_("No partner associated with the contract."))
|
||||
if not self.binary_contract.project.standortpartner.email:
|
||||
raise ValidationError(_("The partner does not have an email address."))
|
||||
# Send email with the binary file as attachment
|
||||
|
||||
def genstamp(self):
|
||||
_logger.info('Create Stamps for Binary: B_'+str(self.id)+' '+str(id))
|
||||
# Bildparameter definieren
|
||||
Medium = self.binary_mediatype
|
||||
if Medium and Medium.can_gen_stamp and self.binary_contract:
|
||||
_logger.info('Create Stamps for Contract : B_'+str(self.id)+' - Contract: C_'+str(self.binary_contract.id)+'- Medium : M_'+str(Medium.id)+' - '+str(Medium.medianame))
|
||||
# Bildgröße und Hintergrundfarbe festlegen
|
||||
background_color = (255, 255, 255) # Weißer Hintergrund (RGB)
|
||||
# Neues Bild erstellen
|
||||
maxh = Medium.maxsize_h
|
||||
maxw = Medium.maxsize_w
|
||||
image = Image.new("RGB", (maxw, maxh), background_color)
|
||||
d = ImageDraw.Draw(image)
|
||||
Zeilen = Medium.maxsize_h // 6
|
||||
zposy = 2
|
||||
if self.binary_contract.client:
|
||||
text = self.binary_contract.contact_company_name
|
||||
_logger.info('Create Stamps for Contract : B_'+str(self.id)+' - Contract: C_'+str(self.binary_contract.id)+'- Medium : M_'+str(Medium.id)+' - Text1: '+str(text))
|
||||
if len(text) > 35:
|
||||
# Trenne den Text an einem Leerzeichen nahe bei Position 40
|
||||
idx = text.rfind(' ', 0, 35)
|
||||
if idx == -1:
|
||||
idx = 35
|
||||
text2 = text[:idx]
|
||||
bcount = len(text2) if text2 else 1
|
||||
fonts = maxw // (bcount ) *1.8
|
||||
if fonts > maxh:
|
||||
fonts = maxh - 10
|
||||
if fonts <=0 :
|
||||
fonts = 10
|
||||
# font = ImageFont.truetype("addons/web/static/fonts/sign/Zeyada-Regular.ttf", fonts)
|
||||
font = ImageFont.truetype("addons/web/static/fonts/google/Open_Sans/Open_Sans-SemiBold.ttf", fonts)
|
||||
d.text((maxw // 2, 1*Zeilen), text2, fill="black",align="center", anchor="ms", font=font) # Beispiel: Ein Rechteck
|
||||
text = text[idx:]
|
||||
zposy = 2
|
||||
if len(text) > 35:
|
||||
# Trenne den Text an einem Leerzeichen nahe bei Position 40
|
||||
idx = text.rfind(' ', 0, 35)
|
||||
if idx == -1:
|
||||
idx = 35
|
||||
text2 = text[:idx]
|
||||
# font = ImageFont.truetype("addons/web/static/fonts/sign/Zeyada-Regular.ttf", fonts)
|
||||
font = ImageFont.truetype("addons/web/static/fonts/google/Open_Sans/Open_Sans-SemiBold.ttf", fonts)
|
||||
d.text((maxw // 2, zposy*Zeilen), text2, fill="black",align="center", anchor="ms", font=font) # Beispiel: Ein Rechteck
|
||||
text = text[idx:]
|
||||
zposy = 3
|
||||
else:
|
||||
bcount = len(text) if text else 1
|
||||
fonts = maxw // (bcount ) *1.8
|
||||
if fonts > maxh:
|
||||
fonts = maxh - 10
|
||||
if fonts <=0 :
|
||||
fonts = 10
|
||||
# font = ImageFont.truetype("addons/web/static/fonts/sign/Zeyada-Regular.ttf", fonts)
|
||||
font = ImageFont.truetype("addons/web/static/fonts/google/Open_Sans/Open_Sans-SemiBold.ttf", fonts)
|
||||
d.text((maxw // 2, zposy*Zeilen), text, fill="black",align="center", anchor="ms", font=font) # Beispiel: Ein Rechteck
|
||||
text = self.binary_contract.contact_street
|
||||
bcount = len(text) if text else 1
|
||||
Zeilen = maxh // 6
|
||||
fonts = maxw // (bcount ) *1.2
|
||||
if fonts > maxh:
|
||||
fonts = maxh - 10
|
||||
if fonts <=0 :
|
||||
fonts = 10
|
||||
# font = ImageFont.truetype("addons/web/static/fonts/sign/Zeyada-Regular.ttf", fonts)
|
||||
font = ImageFont.truetype("addons/web/static/fonts/google/Open_Sans/Open_Sans-Regular.ttf", fonts)
|
||||
d.text((maxw // 2, 4*Zeilen), text, fill="black",align="center", anchor="ms", font=font) # Beispiel: Ein Rechteck
|
||||
text = self.binary_contract.contact_zip+' '+self.binary_contract.contact_city
|
||||
bcount = len(text) if text else 1
|
||||
Zeilen = maxh // 6
|
||||
fonts = maxw // (bcount ) *1.2
|
||||
if fonts > maxh:
|
||||
fonts = maxh - 10
|
||||
if fonts <=0 :
|
||||
fonts = 10
|
||||
# font = ImageFont.truetype("addons/web/static/fonts/sign/Zeyada-Regular.ttf", fonts)
|
||||
font = ImageFont.truetype("addons/web/static/fonts/google/Open_Sans/Open_Sans-Regular.ttf", fonts)
|
||||
d.text((maxw // 2, 5*Zeilen), text, fill="black",align="center", anchor="ms", font=font) # Beispiel: Ein Rechteck
|
||||
# Bild speichern
|
||||
filename = Medium.filepartname+self.binary_contract.contract_auto_id+".png"
|
||||
_logger.info('Create Stamps for Contract : B_'+str(self.id)+' - Contract: C_'+str(self.binary_contract.id)+'- Feld : F_'+str(Medium.id)+' - Filename: '+str(filename))
|
||||
image.save(filename)
|
||||
_logger.info("Stamp file created "+str(filename))
|
||||
_logger.info("Copy file to Binaries B_"+str(self))
|
||||
try:
|
||||
self.binary_binary = base64.b64encode(open(filename, "rb").read())
|
||||
self.binary_filename = filename
|
||||
self.binary_type = 'image/png'
|
||||
self.binary_size = os.path.getsize(filename)
|
||||
self.binary_issaved = False
|
||||
self.binary_secured_ro = False
|
||||
self.binary_used_ro = False
|
||||
finally:
|
||||
_logger.info("Binary inserted "+str(self))
|
||||
cloudpath = self.binary_contract.cloudlink
|
||||
if not cloudpath:
|
||||
raise ValidationError(_("Der Vertrag hat keinen Cloudlink. Bitte überprüfen Sie den Vertrag."))
|
||||
if not Medium.cloudlink:
|
||||
raise ValidationError(_("Der Mediatyp hat keinen Cloudlink. Bitte überprüfen Sie den Mediatyp."))
|
||||
cloudpath = cloudpath + '/' + str(Medium.cloudlink)
|
||||
_logger.info("Copy file to Cloud Path : "+str(cloudpath))
|
||||
try:
|
||||
client = Client("https://cloud.logumedia.de/remote.php/dav/files/OdooDav/", auth=("odooClient@logumedia.de", "lm2020#OdooDav"))
|
||||
try:
|
||||
#client.mkdir(new_folder)
|
||||
#_logger.info("Make Cloud Path : "+str(new_folder))
|
||||
client.upload_file(filename, f"{cloudpath}/{filename}")
|
||||
except Exception as e:
|
||||
_logger.info("Make Cloud Path error : "+str(e))
|
||||
finally:
|
||||
self.binary_issaved = True
|
||||
_logger.info("File copied to Cloud Path : "+str(cloudpath))
|
||||
return True
|
||||
|
||||
Reference in New Issue
Block a user