<commit_before>import ast
import numpy as np
from dateutil import parser
from struct import unpack, calcsize

from laserchicken.io.utils import convert_to_short_type, convert_to_single_character_type


def read(path):
    """
    Read point cloud data from a ply file.
    :param path: path to the ply file
    :return: dictionary containing the point cloud data
    """
    # check whether file is in ascii/binary format
    with open(path, 'r') as ply:
        try:
            _ = ply.readline()
            is_binary = False
        except UnicodeDecodeError:
            is_binary = True

    # read file content
    with open(path, ''.join(['r', 'b' if is_binary else ''])) as ply:
        first_line = _read_header_line(ply, is_binary)

        if 'ply' not in first_line:
            raise ValueError('Not a valid ply file: {}'.format(path))

        index, format = _read_header(ply, is_binary)
        return {block['type']: _read_block(block, ply, format) for block in index}


def _read_header(ply, is_binary=False):
    index = []
    comments = []
    line = _read_header_line(ply, is_binary)
    format = line.split()[1]
    while line.strip() != 'end_header':
        if line.startswith('element'):
            element_type = line.split()[1]
            number_of_elements = int(line.split()[2])
            current_properties = []
            index.append(
                {'type': element_type, 'number_of_elements': number_of_elements, 'properties': current_properties})

        if line.startswith('property'):
            property_type, property_name = line[9:].rstrip().split(' ')
            current_properties.append({'type': property_type, 'name': property_name})

        if line.startswith('comment'):
            comment_line = line.rstrip().split(' ', 1)[1]
            comments.append(comment_line)

        line = _read_header_line(ply, is_binary)
<commit_msg>bug fix: ply reader raises correct error for invalid files<commit_after>import ast
import numpy as np
from dateutil import parser
from struct import unpack, calcsize

from laserchicken.io.utils import convert_to_short_type, convert_to_single_character_type


def read(path):
    """
    Read point cloud data from a ply file.
    :param path: path to the ply file
    :return: dictionary containing the point cloud data
    """
    # check whether file is in ascii/binary format
    is_binary = _is_ply_binary(path)

    # read file content
    with open(path, ''.join(['r', 'b' if is_binary else ''])) as ply:
        first_line = _read_header_line(ply, is_binary)

        if 'ply' not in first_line:
            raise ValueError('Not a valid ply file: {}'.format(path))

        index, format = _read_header(ply, is_binary)
        return {block['type']: _read_block(block, ply, format) for block in index}


def _is_ply_binary(path, is_binary=False):
    is_valid = True
    with open(path, ''.join(['r', 'b' if is_binary else ''])) as ply:
        try:
            _ = _read_header_line(ply, is_binary)
        except UnicodeDecodeError:
            if is_binary:
                is_valid = False
            else:
                return _is_ply_binary(path, is_binary=True)
    if not is_valid:
        raise ValueError('Not a valid ply file: {}'.format(path))
    return is_binary


def _read_header(ply, is_binary=False):
    index = []
    comments = []
    line = _read_header_line(ply, is_binary)
    format = line.split()[1]
    while line.strip() != 'end_header':
        if line.startswith('element'):
            element_type = line.split()[1]
            number_of_elements = int(line.split()[2])
            current_properties = []
            index.append(
                {'type': element_type, 'number_of_elements': number_of_elements, 'properties': current_properties})

        if line.startswith('property'):
            property_type, property_name = line[9:].rstrip().split(' ')
            current_properties.append({'type': property_type, 'name': property_name})

        if line.startswith('comment'):
            comment_line = line.rstrip().split(' ', 1)[1]
            comments.append(comment_line)

        line = _read_header_line(ply, is_binary)

{'fraction_non_alphanumeric': 0.11124430592184129, 'fraction_numerical': 0.0028770079117717575, 'mean_word_length': 2.7687443541102077, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2331883', 'n_tokens_mistral': 1255, 'n_tokens_neox': 1213, 'n_words': 335}