""" Services module """ import requests import json from pyvin import VIN from django.conf import settings from .models import CarMake def get_make(item): """ Fetches a car make object from the database based on the provided item. The function first attempts an exact case-insensitive match on the full string. If no match is found, it splits the input string by spaces and checks for a match with each fragment, stopping as soon as a match is found. :param item: A string representing the name or a part of the name of the car make to search. :type item: str :return: The first matching CarMake object found, or None if no match is found. :rtype: CarMake or None """ data = CarMake.objects.filter(name__iexact=item).first() if not data: r = item.split(" ") for i in r: if data:= CarMake.objects.filter(name__iexact=i).first(): break return data def get_model(item,make): """ Searches for a car model associated with a specific make by performing an exact case-insensitive match. If no match is found, it attempts to match based on individual words split from the input item. :param item: A string representing the name of the car model to search for. :param make: An object representing the car manufacturer, which contains the associated car models. :return: Returns the first car model object that matches the search criteria, or None if no match is found. """ data = make.carmodel_set.filter(name__iexact=item).first() if not data: r = item.split(" ") for i in r: if data:=make.carmodel_set.filter(name__iexact=i).first(): break return data def normalize_name(name): """ Normalizes a given name by removing spaces and hyphens and converting it to lowercase. This function is useful for ensuring consistent formatting of names by removing unwanted characters and applying a uniform casing. The output is designed to be a simple, standardized string version of the input name. :param name: The name string to be normalized. :type name: str :return: A normalized string with no spaces or hyphens, all in lowercase. :rtype: str """ return name.replace(" ", "").replace("-", "").lower() def decodevin(vin): """ Decodes a Vehicle Identification Number (VIN) using multiple decoding functions and returns the decoded result. This function attempts to decode the VIN using three different functions in sequence and returns the first successful result. If none of the decoding functions produce a valid result, the function returns None. :param vin: The Vehicle Identification Number (VIN) to be decoded. :type vin: str :return: The decoded result if any decoding function is successful, or None if all decoding attempts fail. :rtype: dict | None """ if result:=decode_vin(vin): return result elif result:=elm(vin): return result # elif result:=decode_vin_haikalna(vin): # return result else: return None def decode_vin(vin): """ Decodes a given Vehicle Identification Number (VIN) to extract vehicle details such as maker, model, and model year. This function takes a VIN string as input, processes it using the VIN utility, and attempts to extract essential information about the vehicle. It returns a dictionary containing the decoded details if all required fields are successfully retrieved; otherwise, it returns None. :param vin: The Vehicle Identification Number to be decoded. :type vin: str :return: A dictionary containing decoded vehicle details with keys "maker", "model", and "modelYear", or None if any of these fields cannot be determined. :rtype: dict | None """ v = VIN(vin) data = {} if v: data = { "maker": v.Make, "model": v.Model, "modelYear": v.ModelYear, } return data if all([x for x in data.values()]) else None def elm(vin): """ Fetches vehicle information using the provided VIN (Vehicle Identification Number) through the ELM API service. This function sends a GET request to the ELM API endpoint with the VIN parameter to retrieve details about a vehicle, including its maker, model, and model year. The function processes the API's JSON response to extract relevant data and returns it if all required fields are available. :param vin: Vehicle Identification Number required to query the ELM API service for vehicle information. :type vin: str :return: A dictionary containing the vehicle's `maker`, `model`, and `modelYear` if all fields are present. Returns None if any of these fields are missing. :rtype: dict or None """ headers = { "Content-Type": "application/json", "app-id": settings.ELM_APP_ID, "app-key": settings.ELM_APP_KEY, "client-id": settings.ELM_CLIENT_ID, } url = ( "https://vehicle-maintenance.api.elm.sa/api/v1/vehicles/vehicle-info?vin=" + vin ) payload = {} response = requests.request("GET", url, headers=headers, data=payload) response = json.loads(response.text) data = {} if response.get("data"): data = { "maker": response["data"]["maker"], "model": response["data"]["model"] if response["data"]["model"] else " ", "modelYear": response["data"]["modelYear"], } print([x for x in data.values()]) return data if all([x for x in data.values()]) else None