Example #1
0
    def test_dump(self):
        # Arrange
        c = b"abc"
        # Temporarily redirect stdout
        old_stdout = sys.stdout
        sys.stdout = mystdout = StringIO()

        # Act
        IptcImagePlugin.dump(c)

        # Reset stdout
        sys.stdout = old_stdout

        # Assert
        self.assertEqual(mystdout.getvalue(), "61 62 63 \n")
Example #2
0
File: image.py Project: saimn/sigal
def get_iptc_data(filename):
    """Return a dict with the raw IPTC data."""

    logger = logging.getLogger(__name__)

    iptc_data = {}
    raw_iptc = {}

    # PILs IptcImagePlugin issues a SyntaxError in certain circumstances
    # with malformed metadata, see PIL/IptcImagePlugin.py", line 71.
    # ( https://github.com/python-pillow/Pillow/blob/9dd0348be2751beb2c617e32ff9985aa2f92ae5f/src/PIL/IptcImagePlugin.py#L71 )
    try:
        img = _read_image(filename)
        raw_iptc = IptcImagePlugin.getiptcinfo(img)
    except SyntaxError:
        logger.info('IPTC Error in %s', filename)

    # IPTC fields are catalogued in:
    # https://www.iptc.org/std/photometadata/specification/IPTC-PhotoMetadata
    # 2:05 is the IPTC title property
    if raw_iptc and (2, 5) in raw_iptc:
        iptc_data["title"] = raw_iptc[(2, 5)].decode('utf-8', errors='replace')

    # 2:120 is the IPTC description property
    if raw_iptc and (2, 120) in raw_iptc:
        iptc_data["description"] = raw_iptc[(2, 120)].decode('utf-8',
                                                             errors='replace')

    # 2:105 is the IPTC headline property
    if raw_iptc and (2, 105) in raw_iptc:
        iptc_data["headline"] = raw_iptc[(2, 105)].decode('utf-8',
                                                          errors='replace')

    return iptc_data
Example #3
0
    def read_metadata(self, filename):
        try:
            image = Image.open(filename)
            iptc = IptcImagePlugin.getiptcinfo(image)
            metadata = {
                k.strip(): v.strip()
                for (k, v) in
                [kv.decode("utf-8").split(':') for kv in iptc[(2, 25)]]
            }
            return metadata
        except Exception as ex:
            try:
                tags = None
                with open(filename, 'rb') as image_file:
                    tags = exifread.process_file(image_file, debug=True)

                if tags and 'Image ApplicationNotes' in tags:
                    xml = str(tags['Image ApplicationNotes'])
                    xml = ET.fromstring(xml)
                    items = xml.findall(
                        './/{http://www.w3.org/1999/02/22-rdf-syntax-ns#}Bag/{http://www.w3.org/1999/02/22-rdf-syntax-ns#}li'
                    )
                    items = [item.text.split(':') for item in items]
                    items = [(a.strip(), b.strip()) for a, b in items]
                    metadata = dict(items)
                    return metadata

            except Exception as ex2:
                pass

        return None
Example #4
0
    def read_exif(self):
        """Reads relevant exif tags from an image provided as PIL.Image object"""
        image_handle = Image.open(self.image_path)
        exif = image_handle.info["parsed_exif"]
        iptc = IptcImagePlugin.getiptcinfo(image_handle)
        labeled_exifs = label_exifs(exif)
        image_handle = None

        # longitude, latitude
        geotags = get_geotagging(exif)
        self.lon, self.lat = get_coordinates(geotags)

        # date taken
        self._date_taken = datetime.strptime(
            labeled_exifs.get("DateTimeOriginal"),
            "%Y:%m:%d %H:%M:%S",
        )

        # headline
        if not self.skip:
            headline = iptc.get(IPTC_KEYS["headline"])
            if headline is not None:
                self.headline = headline.decode("UTF-8")
            else:
                self.headline = reverse_geocode(self)

            # description
            description = iptc.get(IPTC_KEYS["description"])
            if description is not None:
                self.description = description.decode("UTF-8")
            else:
                self.description = "No description...yet"
Example #5
0
    def expand(self):
        self.fetch_data()
        # Get rating
        # cursor.execute("SELECT AVG(rating) AS average FROM " + tbl_image_rating + " WHERE image = %s GROUP BY image", [imageId])
        # rating = cursor.fetchone()
        # if rating != None:
        #    image['rating'] = rating

        # get author name
        if self.author:
            self.author_name = db.fetch("SELECT name FROM " + db.tbl_author + " WHERE id=%s", [self.author], one=True,
                                        as_list=True)

        # get labels
        labels = db.fetch(
            "SELECT id, name FROM " + db.tbl_label + " INNER JOIN " + db.tbl_image_label + " ON (label = id AND image = %s)",
            [self.id])
        if labels:
            self.labels = labels

        # get meta data
        self.open()
        exif = {}
        iptc = {}
        exif_info = self.image._getexif() or {}
        for tag, value in exif_info.items():
            decoded = ExifTags.TAGS.get(tag, str(tag))
            exif[decoded] = value
        iptc_info = IptcImagePlugin.getiptcinfo(self.image) or {}
        for tag, value in iptc_info.items():
            decoded = iptc_tags.get(tag, str(tag))
            iptc[decoded] = value
        self.exif = exif
        self.iptc = iptc
Example #6
0
def get_iptc_data(filename):
    """Return a dict with the raw IPTC data."""

    logger = logging.getLogger(__name__)

    iptc_data = {}
    raw_iptc = {}

    # PILs IptcImagePlugin issues a SyntaxError in certain circumstances
    # with malformed metadata, see PIL/IptcImagePlugin.py", line 71.
    # ( https://github.com/python-pillow/Pillow/blob/9dd0348be2751beb2c617e32ff9985aa2f92ae5f/src/PIL/IptcImagePlugin.py#L71 )
    try:
        img = _read_image(filename)
        raw_iptc = IptcImagePlugin.getiptcinfo(img)
    except SyntaxError:
        logger.info('IPTC Error in %s', filename)

    # IPTC fields are catalogued in:
    # https://www.iptc.org/std/photometadata/specification/IPTC-PhotoMetadata
    # 2:05 is the IPTC title property
    if raw_iptc and (2, 5) in raw_iptc:
        iptc_data["title"] = raw_iptc[(2, 5)].decode('utf-8', errors='replace')

    # 2:120 is the IPTC description property
    if raw_iptc and (2, 120) in raw_iptc:
        iptc_data["description"] = raw_iptc[(2, 120)].decode('utf-8',
                                                             errors='replace')

    # 2:105 is the IPTC headline property
    if raw_iptc and (2, 105) in raw_iptc:
        iptc_data["headline"] = raw_iptc[(2, 105)].decode('utf-8',
                                                          errors='replace')

    return iptc_data
Example #7
0
def get_meta_iptc(file_stream):
    """Returns the image IPTC metadata in a dictionary of tag:value pairs.

    @param file_stream: stream
    """
    file_stream.seek(0)
    img = Image.open(file_stream)
    iptc_raw = IptcImagePlugin.getiptcinfo(img)
    metadata = {}

    if iptc_raw is None:
        return metadata

    for code, value in iptc_raw.items():
        try:
            tag = iim_codes[code]
        except KeyError:
            continue
        if isinstance(value, list):
            try:
                value = [v.decode('utf-8') for v in value]
            except UnicodeDecodeError:
                pass
        elif isinstance(value, bytes):
            try:
                value = value.decode('utf-8')
            except UnicodeDecodeError:
                pass
        metadata[tag] = value
    return metadata
Example #8
0
    def test_getiptcinfo_tiff_none(self):
        # Arrange
        im = Image.open("Tests/images/hopper.tif")

        # Act
        iptc = IptcImagePlugin.getiptcinfo(im)

        # Assert
        self.assertIsNone(iptc)
Example #9
0
    def test_getiptcinfo_tiff_none(self):
        # Arrange
        im = Image.open("Tests/images/hopper.tif")

        # Act
        iptc = IptcImagePlugin.getiptcinfo(im)

        # Assert
        self.assertIsNone(iptc)
Example #10
0
    def test_getiptcinfo_jpg_none(self):
        # Arrange
        im = hopper()

        # Act
        iptc = IptcImagePlugin.getiptcinfo(im)

        # Assert
        self.assertIsNone(iptc)
Example #11
0
def test_getiptcinfo_jpg_none():
    # Arrange
    with hopper() as im:

        # Act
        iptc = IptcImagePlugin.getiptcinfo(im)

    # Assert
    assert iptc is None
Example #12
0
    def test_getiptcinfo_jpg_none(self):
        # Arrange
        im = hopper()

        # Act
        iptc = IptcImagePlugin.getiptcinfo(im)

        # Assert
        self.assertIsNone(iptc)
Example #13
0
    def test_i(self):
        # Arrange
        c = b"a"

        # Act
        ret = IptcImagePlugin.i(c)

        # Assert
        self.assertEqual(ret, 97)
Example #14
0
def test_i():
    # Arrange
    c = b"a"

    # Act
    ret = IptcImagePlugin.i(c)

    # Assert
    assert ret == 97
Example #15
0
def test_getiptcinfo_tiff_none():
    # Arrange
    with Image.open("Tests/images/hopper.tif") as im:

        # Act
        iptc = IptcImagePlugin.getiptcinfo(im)

    # Assert
    assert iptc is None
Example #16
0
    def test_i(self):
        # Arrange
        c = b"a"

        # Act
        ret = IptcImagePlugin.i(c)

        # Assert
        self.assertEqual(ret, 97)
Example #17
0
    def test_getiptcinfo_jpg_found(self):
        # Arrange
        im = Image.open(TEST_FILE)

        # Act
        iptc = IptcImagePlugin.getiptcinfo(im)

        # Assert
        self.assertIsInstance(iptc, dict)
        self.assertEqual(iptc[(2, 90)], b"Budapest")
        self.assertEqual(iptc[(2, 101)], b"Hungary")
Example #18
0
    def test_getiptcinfo_jpg_found(self):
        # Arrange
        im = Image.open(TEST_FILE)

        # Act
        iptc = IptcImagePlugin.getiptcinfo(im)

        # Assert
        self.assertIsInstance(iptc, dict)
        self.assertEqual(iptc[(2, 90)], b"Budapest")
        self.assertEqual(iptc[(2, 101)], b"Hungary")
Example #19
0
    def test_dump(self):
        # Arrange
        c = b"abc"
        # Temporarily redirect stdout
        try:
            from cStringIO import StringIO
        except ImportError:
            from io import StringIO
        import sys
        old_stdout = sys.stdout
        sys.stdout = mystdout = StringIO()

        # Act
        IptcImagePlugin.dump(c)

        # Reset stdout
        sys.stdout = old_stdout

        # Assert
        self.assertEqual(mystdout.getvalue(), "61 62 63 \n")
Example #20
0
def test_getiptcinfo_jpg_found():
    # Arrange
    with Image.open(TEST_FILE) as im:

        # Act
        iptc = IptcImagePlugin.getiptcinfo(im)

    # Assert
    assert isinstance(iptc, dict)
    assert iptc[(2, 90)] == b"Budapest"
    assert iptc[(2, 101)] == b"Hungary"
Example #21
0
def get_iptc_data(filename):
    """Return a dict with the raw IPTC data."""

    img = _read_image(filename)
    raw_iptc = IptcImagePlugin.getiptcinfo(img)
    # IPTC fields are catalogued in:
    # https://www.iptc.org/std/photometadata/specification/IPTC-PhotoMetadata
    iptc_data = {}
    # 2:05 is the IPTC title property
    if raw_iptc and (2, 5) in raw_iptc:
        iptc_data["title"] = raw_iptc[(2, 5)].decode('utf-8')

    # 2:120 is the IPTC description property
    if raw_iptc and (2, 120) in raw_iptc:
        iptc_data["description"] = raw_iptc[(2, 120)].decode('utf-8')

    return iptc_data
Example #22
0
    def extractIptc(self, image):
        iptc = {}

        iptc_tags = {
            (1, 90): 'CodedCharacterSet',
            (2, 0): 'Whatever',
            (2, 5): 'ObjectName',
            (2, 10): 'Urgency',
            (2, 15): 'Category',
            (2, 20): 'Subcategories',
            (2, 25): 'Keywords',
            (2, 40): 'SecialInstructions',
            (2, 55): 'CreationDate',
            (2, 60): 'CreationTime',
            (2, 62): 'DigitizationDate',
            (2, 80): 'AuthorByline',
            (2, 85): 'AuthorTitle',
            (2, 90): 'City',
            (2, 92): 'SubLocation',
            (2, 95): 'State',
            (2, 100): 'CountryCode',
            (2, 101): 'Country',
            (2, 103): 'OTR',
            (2, 105): 'Headline',
            (2, 110): 'Source',
            (2, 115): 'PhotoSource',
            (2, 116): 'Copyright',
            (2, 120): 'Caption',
            (2, 122): 'CaptionWriter',
        }

        iptc_info = IptcImagePlugin.getiptcinfo(image) or {}

        for tag, value in iptc_info.items():
            decoded = iptc_tags.get(tag, str(tag))
            if isinstance(value, (bytes, bytearray)):
                iptc[decoded] = value.decode('utf-8')
            elif isinstance(value, (list)):
                for k, v in enumerate(value):
                    value[k] = v.decode('utf-8')
                iptc[decoded] = value
            else:
                iptc[decoded] = str(value)

        self.metaData[self.currentFile]['iptc'] = iptc
Example #23
0
    def get_iptc_metadata(self, image_file_path):
        """
        Reads the IPTC metadata of an image given by 'image_file_path' and returns it.
        Returns empty array if IPTC metadata is not available.
        :param image_file_path:
        :return iptc:
        """

        logger.debug('get_iptc_metadata()')

        try:
            im = PIL.Image.open(image_file_path)
            iptc = IptcImagePlugin.getiptcinfo(im)
            im.close()
            if not iptc is None:
                return iptc
            else:
                return []
        except:
            e = sys.exc_info()[0]
            logger.debug('is_image_landscape() - {}'.format(e))
Example #24
0
def get_image_metadata(path):
    metadata = {'Exif.Image.Rating': None, 'Iptc.Application2.Keywords': []}

    exif, iptc = None, None

    try:
        image = Image.open(path)
        exif = image._getexif()
        iptc = IptcImagePlugin.getiptcinfo(image)
        image = None
    except:
        log.error("Error loading metadata: %s" % path)

    if exif and exif.has_key(EXIF_IMAGE_RATING_RAW):
        metadata[RATING] = exif[EXIF_IMAGE_RATING_RAW]
    if iptc and iptc.has_key(IPTC_APPLICATION2_KEYWORDS_RAW):
        metadata[TAGS] = iptc[IPTC_APPLICATION2_KEYWORDS_RAW]
        if isinstance(metadata[TAGS], str):
            metadata[TAGS] = [metadata[TAGS]]
    metadata[TAGS] = set(metadata[TAGS])
    return metadata
Example #25
0
def get_image_metadata(path):
    metadata = {'Exif.Image.Rating': None,
                'Iptc.Application2.Keywords': []}

    exif, iptc = None, None

    try:
        image = Image.open(path)
        exif = image._getexif()
        iptc = IptcImagePlugin.getiptcinfo(image)
        image = None
    except:
        log.error("Error loading metadata: %s" % path)

    if exif and exif.has_key(EXIF_IMAGE_RATING_RAW):
        metadata[RATING] = exif[EXIF_IMAGE_RATING_RAW]
    if iptc and iptc.has_key(IPTC_APPLICATION2_KEYWORDS_RAW):
        metadata[TAGS] = iptc[IPTC_APPLICATION2_KEYWORDS_RAW]
        if isinstance(metadata[TAGS], str):
            metadata[TAGS] = [metadata[TAGS]]
    metadata[TAGS] = set(metadata[TAGS])
    return metadata
Example #26
0
def get_meta_iptc(file_stream):
    """Returns the image IPTC metadata in a dictionary of tag:value pairs.

    @param file_stream: stream
    """
    file_stream.seek(0)
    img = Image.open(file_stream)
    iptc_raw = IptcImagePlugin.getiptcinfo(img)
    metadata = {}

    if iptc_raw is None:
        return metadata

    for code, value in iptc_raw.items():
        try:
            tag = iim_codes[code]
        except KeyError:
            continue
        if isinstance(value, list):
            value = [decode(v) for v in value]
        elif isinstance(value, bytes):
            value = decode(value)
        metadata[tag] = value
    return metadata
Example #27
0
def get_caption(image):
    iptc = IptcImagePlugin.getiptcinfo(image)
    return iptc.get((2, 5)).decode()
Example #28
0
    @staticmethod
    def mdget(phile):
        try:
            im = Image.open(phile)
        except IOError, why:
            sys.stderr.write("Can't find metadata for %s (%s).\n" %
                (phile, why)
            )
            return None
        out = {}
        exif_info = im._getexif() or {}
        for tag, value in exif_info.items():
            decoded = ExifTags.TAGS.get(tag, "unknown")
            out["Exif." + decoded] = value
        iptc_info = IptcImagePlugin.getiptcinfo(im) or {}
        for tag, value in iptc_info.items():
            decoded = PhotoWebber._iptc_tags.get(tag, "unknown")
            out["Iptc." + decoded] = value
        return out, im.size

    @staticmethod
    def error(msg):
        "Something has gone horribly wrong."
        sys.stderr.write("FATAL: %s\n" % msg)
        sys.exit(1)


def photoweb_cli():
    "Run command-line photoweb."
    usage   = "Usage: %prog [options] <dir>"
Example #29
0
def pil(file_path: str):
    from PIL import Image, IptcImagePlugin

    im = Image.open(file_path)
    meta = IptcImagePlugin.getiptcinfo(im)
    pprint(meta)
Example #30
0
    def update_metadata(self):
        self.open()

        iptc_info = IptcImagePlugin.getiptcinfo(self.image) or {}
        exif_info = self.image._getexif() or {}

        fields = []
        values = []

        if IPTC_OBJECT_NAME in iptc_info:
            title = iptc_info[IPTC_OBJECT_NAME].decode('utf-8')
            fields.append("description")
            values.append(title)

        timestamp = None
        if IPTC_DATE_CREATED in iptc_info and IPTC_TIME_CREATED in iptc_info:
            timestamp_str = iptc_info[IPTC_DATE_CREATED].decode('utf-8') + iptc_info[IPTC_TIME_CREATED].decode('utf-8')
            if len(timestamp_str) == 14:
                timestamp_str = timestamp_str + '+0000'
            timestamp = datetime.strptime(timestamp_str, '%Y%m%d%H%M%S%z')
        elif EXIF_DATE_TIME_ORIGINAL in exif_info:
            timestamp_str = exif_info[EXIF_DATE_TIME_ORIGINAL]
            if len(timestamp_str) == 19:
                timestamp_str = timestamp_str + '+0000'
            elif timestamp_str[-3] == ':':
                timestamp_str = kill_char(timestamp_str, len(timestamp_str)-3)
            timestamp = datetime.strptime(timestamp_str, '%Y:%m:%d %H:%M:%S%z')
        elif EXIF_DATE_TIME_DIGITIZED in exif_info:
            timestamp_str = exif_info[EXIF_DATE_TIME_DIGITIZED]
            timestamp = datetime.strptime(timestamp_str, '%Y:%m:%d %H:%M:%S')
        if timestamp:
            fields.append("stime")
            values.append(timestamp)

        if IPTC_BYLINE in iptc_info:
            author_name = iptc_info[IPTC_BYLINE].decode('utf-8')
            author_id = db.fetch("SELECT id FROM " + db.tbl_author + " WHERE name=%s", [author_name], one=True,
                                 as_list=True)
            if not author_id:
                author_id = db.execute("INSERT INTO " + db.tbl_author + "(name) VALUES (%s) RETURNING id",
                                       [author_name])
            fields.append("author")
            values.append(author_id)

        if IPTC_KEYWORDS in iptc_info:
            labels = []
            if isinstance(iptc_info[IPTC_KEYWORDS], list):
                for label in iptc_info[IPTC_KEYWORDS]:
                    labels.append(label.decode('utf-8'))
            else:
                labels.append(iptc_info[IPTC_KEYWORDS].decode('utf-8'))
            self.set_labels(labels)

        fields.append("width")
        values.append(self.image.width)
        fields.append("height")
        values.append(self.image.height)

        if fields:
            values.append(self.id)
            fields_str = ", ".join(map(lambda x: "%s=%%s" % x, fields))
            db.execute("UPDATE " + db.tbl_image + " SET " + fields_str + " WHERE id=%s", values)
            db.commit()