from fastapi.exceptions import HTTPException from sqlalchemy import ( String, Integer, Boolean, ForeignKey, Index, Identity, TIMESTAMP, func, ) from sqlalchemy.orm import mapped_column, relationship, Mapped from Commons.select_functions import SelectAction # from ApiLayers.ApiValidations.Custom.token_objects import EmployeeTokenObject # from ApiLayers.ApiValidations.Request import ( # InsertCompany, # UpdateCompany, # MatchCompany2Company, # ) from Services.PostgresService.controllers.mixin_controllers import CrudCollection class RelationshipDutyCompany(CrudCollection): """ CompanyRelationship class based on declarative_base and CrudCollection via session Company -> Sub Company -> Sub-Sub Company if owner_id == parent_id: can manipulate data of any record else: Read-Only duty_id = if relationship_type == base An organization / not operational / no responsible person relationship = company_id filter -> Action filter(company_id) relationship_type = Organization relationship = company_id filter -> Action filter(company_id) relationship_type = Commercial """ __tablename__ = "relationship_duty_company" __exclude__fields__ = [] owner_id: Mapped[int] = mapped_column( ForeignKey("companies.id"), nullable=False ) # 1 duties_id: Mapped[int] = mapped_column( ForeignKey("duties.id"), nullable=False ) # duty -> (n)employee Evyos LTD member_id: Mapped[int] = mapped_column( ForeignKey("companies.id"), nullable=False ) # 2, 3, 4 parent_id: Mapped[int] = mapped_column( ForeignKey("companies.id"), nullable=True ) # None relationship_type: Mapped[str] = mapped_column( String, nullable=True, server_default="Commercial" ) # Commercial, Organization # Bulk child_count: Mapped[int] = mapped_column(Integer) # 0 show_only: Mapped[bool] = mapped_column(Boolean, server_default="0") # related_company: Mapped[List["Companies"]] = relationship( # "Companies", # back_populates="related_companies", # foreign_keys=[related_company_id], # ) # # @classmethod # def match_company_to_company_commercial(cls, data: MatchCompany2Company, token): # from Schemas import ( # Duties, # ) # # token_duties_id, token_company_id = token.get("duty_id"), token.get( # "company_id" # ) # list_match_company_id = [] # send_duties = Duties.filter_one( # Duties.uu_id == data.duty_uu_id, # ) # send_user_duties = Duties.filter_one( # Duties.duties_id == send_duties.id, # Duties.company_id == token_duties_id, # ) # if not send_user_duties: # raise Exception( # "Send Duty is not found in company. Please check duty uuid and try again." # ) # # for company_uu_id in list(data.match_company_uu_id): # company = Companies.filter_one( # Companies.uu_id == company_uu_id, # ) # bulk_company = RelationshipDutyCompany.filter_one( # RelationshipDutyCompany.owner_id == token_company_id, # RelationshipDutyCompany.relationship_type == "Bulk", # RelationshipDutyCompany.member_id == company.id, # ) # if not bulk_company: # raise Exception( # f"Bulk Company is not found in company. " # f"Please check company uuid {bulk_company.uu_id} and try again." # ) # list_match_company_id.append(bulk_company) # # for match_company_id in list_match_company_id: # RelationshipDutyCompany.find_or_create( # owner_id=token_company_id, # duties_id=send_user_duties.id, # member_id=match_company_id.id, # parent_id=match_company_id.parent_id, # relationship_type="Commercial", # show_only=False, # ) # # @classmethod # def match_company_to_company_organization(cls, data: MatchCompany2Company, token): # from Schemas import ( # Duties, # ) # # token_duties_id, token_company_id = token.get("duty_id"), token.get( # "company_id" # ) # list_match_company_id = [] # send_duties = Duties.filter_one( # Duties.uu_id == data.duty_uu_id, # ) # send_user_duties = Duties.filter_one( # Duties.duties_id == send_duties.id, # Duties.company_id == token_duties_id, # ) # if not send_user_duties: # raise Exception( # "Send Duty is not found in company. Please check duty uuid and try again." # ) # # for company_uu_id in list(data.match_company_uu_id): # company = Companies.filter_one( # Companies.uu_id == company_uu_id, # ) # bulk_company = RelationshipDutyCompany.filter_one( # RelationshipDutyCompany.owner_id == token_company_id, # RelationshipDutyCompany.relationship_type == "Bulk", # RelationshipDutyCompany.member_id == company.id, # ) # if not bulk_company: # raise Exception( # f"Bulk Company is not found in company. " # f"Please check company uuid {bulk_company.uu_id} and try again." # ) # list_match_company_id.append(bulk_company) # # for match_company_id in list_match_company_id: # Duties.init_a_company_default_duties( # company_id=match_company_id.id, # company_uu_id=str(match_company_id.uu_id), # ) # RelationshipDutyCompany.find_or_create( # owner_id=token_company_id, # duties_id=send_user_duties.id, # member_id=match_company_id.id, # parent_id=match_company_id.parent_id, # relationship_type="Organization", # show_only=False, # ) # # __table_args__ = ( # Index( # "_company_relationship_ndx_01", # duties_id, # owner_id, # member_id, # relationship_type, # unique=True, # ), # {"comment": "Company Relationship Information"}, # ) class Companies(CrudCollection, SelectAction): """ Company class based on declarative_base and CrudCollection via session formal_name = Government register name by offical public_name = Public registered name by User nick_name = Search by nickname, commercial_type = Tüzel veya birey """ __tablename__ = "companies" __exclude__fields__ = ["is_blacklist", "is_commercial"] __access_by__ = [] __many__table__ = RelationshipDutyCompany # __explain__ = AbstractCompany() formal_name: Mapped[str] = mapped_column( String, nullable=False, comment="Formal Name" ) company_type: Mapped[str] = mapped_column( String, nullable=False, comment="Company Type" ) commercial_type: Mapped[str] = mapped_column( String, nullable=False, comment="Commercial Type" ) tax_no: Mapped[str] = mapped_column( String, index=True, unique=True, nullable=False, comment="Tax No" ) public_name: Mapped[str] = mapped_column(String, comment="Public Name of a company") company_tag: Mapped[str] = mapped_column(String, comment="Company Tag") default_lang_type: Mapped[str] = mapped_column(String, server_default="TR") default_money_type: Mapped[str] = mapped_column(String, server_default="TL") is_commercial: Mapped[bool] = mapped_column(Boolean, server_default="False") is_blacklist: Mapped[bool] = mapped_column(Boolean, server_default="False") parent_id = mapped_column(Integer, nullable=True) workplace_no: Mapped[str] = mapped_column(String, nullable=True) official_address_id: Mapped[int] = mapped_column( ForeignKey("addresses.id"), nullable=True ) official_address_uu_id: Mapped[str] = mapped_column( String, nullable=True, comment="Official Address UUID" ) top_responsible_company_id: Mapped[int] = mapped_column( ForeignKey("companies.id"), nullable=True ) top_responsible_company_uu_id: Mapped[str] = mapped_column( String, nullable=True, comment="Top Responsible Company UUID" ) # buildings: Mapped[List["Build"]] = relationship( # "Build", # back_populates="companies", # foreign_keys="Build.company_id", # ) __table_args__ = ( Index("_company_ndx_01", tax_no, unique=True), Index("_company_ndx_02", formal_name, public_name), {"comment": "Company Information"}, ) # # @classmethod # def create_action(cls, data: InsertCompany, token: EmployeeTokenObject): # from Schemas import Addresses, Duties # # data_dict = data.model_dump() # if cls.filter_one(cls.tax_no == str(data.tax_no).strip(), system=True).data: # raise HTTPException( # status_code=400, # detail="Company already exists. Please ask supervisor to make company visible for your duty.", # ) # # official_address = Addresses.filter_one( # Addresses.uu_id == data.official_address_uu_id, # ).data # # if not official_address: # # raise HTTPException( # # status_code=400, # # detail="Official address is not found. Please check address uuid and try again.", # # ) # # bulk_duties = Duties.get_bulk_duties_of_a_company( # company_id=token.selected_company.company_id # ) # # if official_address: # data_dict["official_address_id"] = official_address.id # data_dict["official_address_uu_id"] = str(official_address.uu_id) # # data_dict["parent_id"] = token.selected_company.company_id # data_dict["top_responsible_company_id"] = token.selected_company.company_id # data_dict["top_responsible_company_uu_id"] = ( # token.selected_company.company_uu_id # ) # company_created = cls.find_or_create(**data_dict) # company_created.save_and_confirm() # company_relationship_created = RelationshipDutyCompany.find_or_create( # owner_id=token.selected_company.company_id, # duties_id=bulk_duties.id, # member_id=company_created.id, # parent_id=company_created.parent_id, # child_count=0, # relationship_type="Bulk", # show_only=False, # ) # company_relationship_created.save_and_confirm() # return company_created # # @classmethod # def update_action(cls, data: UpdateCompany, token): # from Schemas import ( # Addresses, # ) # # data_dict = data.excluded_dump() # duty_id = token.get("duty_id") # company_id = token.get("company_id") # if data.official_address_uu_id: # official_address = Addresses.filter_one( # Addresses.uu_id == data.official_address_uu_id, # *Addresses.valid_record_args(Addresses), # ).data # data_dict["official_address_id"] = official_address.id # del data_dict["official_address_uu_id"], data_dict["company_uu_id"] # company_to_update = cls.select_action( # duty_id_list=[duty_id], # filter_expr=[ # cls.uu_id == data.company_uu_id, # RelationshipDutyCompany.parent_id == company_id, # ], # ) # return company_to_update.update(**data_dict) # parent_id = mapped_column(ForeignKey("companies.id")) # if data.parent_uu_id: # company = Companies.find_one(uu_id=data.parent_uu_id) # data_dict["parent_id"] = company.id # def is_access_valid(self, endpoint_ext: str): # try: # if ( # not arrow.get(self.stop_date) # > arrow.utcnow() # > arrow.get(self.start_date) # ): # message = f"Kullanıcı yetkileri süresi dolmuştur. {self.endpoint_name} için supervisor ile görüşünüz." # SystemLogs.create_log( # log_type="ERROR", # log_code="ACCESS_EXPIRED", # log_action=self.__tablename__, # log_message=message, # ) # return False # except Exception as e: # SystemLogs.create_log( # log_type="ERROR", # log_code="ACCESS_EXPIRED", # log_action=self.__tablename__, # log_message=e, # ) # return False # # access_dict = { # "LIST": self.access_read, # "INSERT": self.access_write, # "UPDATE": self.access_update, # "DELETE": self.access_delete, # "ACTIVE": self.access_update, # "PRINT": self.report_print, # "EXPORT": self.report_export, # } # return access_dict.get(endpoint_ext.upper(), False) # official_address: Mapped[List["Address"]] = relationship( # "Address", # back_populates="official_companies", # foreign_keys=[official_address_id], # ) # # emails: Mapped[List["UsersEmails"]] = relationship( # "UsersEmails", back_populates="companies", foreign_keys="UsersEmails.company_id" # ) # phones: Mapped[List["UsersPhones"]] = relationship( # "UsersPhones", back_populates="company", foreign_keys="UsersPhones.company_id" # ) # buildings: Mapped[List["Build"]] = relationship( # "Build", # back_populates="companies", # foreign_keys="Build.company_id", # ) # response_buildings: Mapped[List["Build"]] = relationship( # "Build", # back_populates="response_companies", # foreign_keys="Build.response_company_id", # ) # departments: Mapped[List["CompanyDepartments"]] = relationship( # "CompanyDepartments", # back_populates="company", # foreign_keys="CompanyDepartments.company_id", # ) # budget_records: Mapped[List["CompanyBudgetRecords"]] = relationship( # "CompanyBudgetRecords", # back_populates="companies", # foreign_keys="CompanyBudgetRecords.company_id", # ) # send_budget_records: Mapped[List["CompanyBudgetRecords"]] = relationship( # "CompanyBudgetRecords", # back_populates="send_companies", # foreign_keys="CompanyBudgetRecords.send_company_id", # ) # decision_books: Mapped[List["BuildDecisionBook"]] = relationship( # "BuildDecisionBook", # back_populates="companies", # foreign_keys="BuildDecisionBook.resp_company_id", # ) # decision_book_projects: Mapped[List["BuildDecisionBookProjects"]] = relationship( # "BuildDecisionBookProjects", # back_populates="companies", # foreign_keys="BuildDecisionBookProjects.resp_company_id", # ) # decision_book_legal: Mapped["BuildDecisionBookLegal"] = relationship( # "BuildDecisionBookLegal", # back_populates="attorney_companies", # foreign_keys="BuildDecisionBookLegal.resp_attorney_company", # ) # # company_account_books: Mapped["AccountBooks"] = relationship( # "AccountBooks", # back_populates="company", # foreign_keys="AccountBooks.company_id", # ) # branch_account_books: Mapped["AccountBooks"] = relationship( # "AccountBooks", # back_populates="branch", # foreign_keys="AccountBooks.branch_id", # ) # account_codes: Mapped["AccountCodes"] = relationship( # "AccountCodes", back_populates="company", foreign_keys="AccountCodes.company_id" # ) # search_iban_description: Mapped["BuildIbanDescription"] = relationship( # "BuildIbanDescription", # back_populates="company", # foreign_keys="BuildIbanDescription.company_id", # ) # related_companies: Mapped[List["CompanyRelationship"]] = relationship( # "CompanyRelationship", # back_populates="related_company", # foreign_keys="CompanyRelationship.related_company_id", # ) # # class AbstractCompany: # """ # Abstract and explanation of Company class for end-user guide # """ # # formal_name = Explanation( # explanation="Devletin resmi kayıtlarında bulunan şirket ünvanıdır.", # usage="Devletin resmi kayıtlarında bulunan şirket adı istendiğinde kullanılır.", # alias="Resmi Ünvan", # example=["X Şirketi LTD", "Y Şirketi A.Ş."], # ) # company_type = Explanation( # explanation="Şirketin türüdür.", # usage="Şirketin türü istendiğinde kullanılır.", # alias="Şirket Türü", # example=[ # "Şahıs", # "Limited", # "Anonim", # "Kolektif", # "Komandit", # "Kooperatif", # "Serbest Meslek", # "Adi Ortaklık", # ], # ) # commercial_type = Explanation( # explanation="Şirketin ticari türüdür.", # usage="Şirketin ticari türü istendiğinde kullanılır.", # alias="Ticari Tür", # example=["Tüzel", "Birey"], # ) # tax_no = Explanation( # explanation="Şirketin vergi numarasıdır.", # usage="Şirketin vergi numarası istendiğinde kullanılır.", # alias="Vergi No", # example=["1234567890"], # ) # public_name = Explanation( # explanation="Şirketin kamuoyunda bilinen adıdır.", # usage="Şirketin kamuoyunda bilinen adı istendiğinde kullanılır.", # alias="Piyasada Bilinen Adı", # example=["X Şirketi", "Y Şirketi"], # ) # company_tag = Explanation( # explanation="Şirketin takma adı veya etiketidir.", # usage="Şirketin yöneticisin karar verdiği takma adı veya etiketi istendiğinde kullanılır.", # alias="Şirket Etiketi veya Takma Adı", # example=["X", "Y"], # ) # default_lang_type = Explanation( # explanation="Şirketin varsayılan dil türüdür.", # usage="Şirketin varsayılan dil türü istendiğinde kullanılır.", # alias="Şirketin Dil Türü", # example=["TR", "EN"], # ) # default_money_type = Explanation( # explanation="Şirketin varsayılan para birimi türüdür.", # usage="Şirketin varsayılan para birimi türü istendiğinde kullanılır.", # alias="Şirketin Para Birimi Türü", # example=["TL", "USD", "EUR"], # ) # is_commercial = Explanation( # explanation="Şirketin ticari olup olmadığını belirtir.", # usage="Şirketin ticari olup olmadığını applikasyonun anlaması için kullanılır.", # condition=lambda commercial_type: True if commercial_type == "Şahıs" else False, # alias="Şirket Ticari mi?", # ) # is_blacklist = Explanation( # explanation="Şirketin kara listeye alınıp alınmadığını belirtir.", # usage="Şirketin kara listeye alınıp alınmadığını applikasyonun anlaması için kullanılır.", # alias="Kara Listeye alınsın mı?", # example=[True, False], # ) # parent_id = Explanation( # explanation="Şirketin sorumlu olduğu şirketin ID'sidir.", # usage="Şirketin sorumlu olduğu şirketin ID'si istendiğinde kullanılır.", # alias="Sorumlu Şirket", # example=[ # "Bir şirketin sorumlu şirketi hangisi olduğunu bulmak için kullanılır.", # ], # ) # workplace_no = Explanation( # explanation="Şirketin iş yeri numarasıdır.", # usage="Şirketin iş yeri numarası istendiğinde kullanılır.", # alias="İş Yeri No", # example=["1234567890"], # ) # official_address_id = Explanation( # explanation="Şirketin resmi adresidi.", # usage="Şirketin resmi adresinin ne olduğunu bulmak için kullanılır.", # alias="Resmi Adres", # example=[ # "Bu şirketin adresi nedir sorusuna cevap vermek için kullanılır.", # ], # ) # top_responsible_company_id = Explanation( # explanation="Şirketin en üst sorumlu şirketin ID'sidir.", # usage="Şirketin en üst sorumlu şirketin hangisi olduğunu bulmak için kullanılır.", # alias="Ana Yetkili Şirket", # example=[ # "Bölge veya ülke genelinde en üst sorumlu şirketin hangisi olduğunu belirtmek için kullanılır.", # ], # ) # buildings = Explanation( # explanation="Şirketin sahip olduğu binaların listesidir.", # usage="Şirketin sahip olduğu binaların listesini bulmak için kullanılır.", # alias="Sorumlu olduğu binalar Binalar", # example=[ # "Şirketin sahip olduğu binaların listesini bulmak için kullanılır.", # ], # ) # # def wag_create_company(self): # """ # Er kişiye wag_create_company fonksiyonu = fieldları manipule edebilir? # 78 ile oluşturulan bir user için wag_create_company fonksiyonu = fieldları manipule edebilir? # """ # return { # "commercial_type": self.commercial_type, # "formal_name": self.formal_name, # "public_name": self.public_name, # "company_type": self.company_type, # "tax_no": self.tax_no, # "workplace_no": self.workplace_no, # "company_tag": self.company_tag, # "default_lang_type": self.default_lang_type, # "default_money_type": self.default_money_type, # "official_address_id": self.official_address_id, # } # # def wag_update_company(self): # return { # "commercial_type": self.commercial_type, # "formal_name": self.formal_name, # "public_name": self.public_name, # "company_type": self.company_type, # "tax_no": self.tax_no, # "workplace_no": self.workplace_no, # "company_tag": self.company_tag, # "default_lang_type": self.default_lang_type, # "default_money_type": self.default_money_type, # "official_address_id": self.official_address_id, # }