def setUp(self):
     self.formatter = NewsroomNinjsFormatter()
     init_app(self.app)
     self.maxDiff = None
class NinjsFormatterTest(TestCase):
    def setUp(self):
        self.formatter = NewsroomNinjsFormatter()
        init_app(self.app)
        self.maxDiff = None

    def test_products(self):
        self.app.data.insert(
            'content_filters',
            [{
                "_id": 3,
                "content_filter": [{
                    "expression": {
                        "pf": [1],
                        "fc": [2]
                    }
                }],
                "name": "soccer-only3"
            }])
        self.app.data.insert('filter_conditions', [{
            '_id': 1,
            'field': 'headline',
            'operator': 'like',
            'value': 'test',
            'name': 'test-1'
        }])
        self.app.data.insert('filter_conditions', [{
            '_id': 2,
            'field': 'urgency',
            'operator': 'in',
            'value': '2',
            'name': 'test-2'
        }])
        self.app.data.insert('products', [{
            "_id": 1,
            "content_filter": {
                "filter_id": 3,
                "filter_type": "permitting"
            },
            "name": "p-1",
            "product_type": "api"
        }])
        self.app.data.insert('vocabularies', [{
            "_id":
            "locators",
            "display_name":
            "Locators",
            "type":
            "unmanageable",
            "unique_field":
            "qcode",
            "items": [
                {
                    "is_active": True,
                    "name": "NSW",
                    "qcode": "NSW",
                    "state": "New South Wales",
                    "country": "Australia",
                    "world_region": "Oceania",
                    "group": "Australia"
                },
            ],
        }])
        embargo_ts = (utcnow() + timedelta(days=2))
        article = {
            '_id':
            'tag:aap.com.au:20150613:12345',
            'guid':
            'tag:aap.com.au:20150613:12345',
            '_current_version':
            1,
            'anpa_category': [{
                'qcode': 'a'
            }],
            'source':
            'AAP',
            'headline':
            'This is a test headline',
            'byline':
            'joe',
            'slugline':
            'slugline',
            'subject': [{
                'qcode': '02011001',
                'name': 'international court or tribunal',
                'parent': None
            }, {
                'qcode': '02011002',
                'name': 'extradition'
            }],
            'anpa_take_key':
            'take_key',
            'unique_id':
            '1',
            'body_html':
            'The story body',
            'type':
            'text',
            'word_count':
            '1',
            'priority':
            1,
            'profile':
            'snap',
            'state':
            'published',
            'urgency':
            2,
            'pubstatus':
            'usable',
            'creditline':
            'sample creditline',
            'keywords': ['traffic'],
            'abstract':
            '<p>sample <b>abstract</b></p>',
            'place': [{
                'name': 'NSW',
                'qcode': 'NSW'
            }],
            'embargo':
            embargo_ts,
            'body_footer':
            '<p>call helpline 999 if you are planning to quit smoking</p>',
            'company_codes': [{
                'name': 'YANCOAL AUSTRALIA LIMITED',
                'qcode': 'YAL',
                'security_exchange': 'ASX'
            }],
            'genre': [{
                'name': 'Article',
                'qcode': 'article'
            }],
            'flags': {
                'marked_for_legal': True
            },
            'extra': {
                'foo': 'test'
            },
            'operation':
            'publish'
        }
        seq, doc = self.formatter.format(article,
                                         {'name': 'Test Subscriber'})[0]
        expected = {
            "guid":
            "tag:aap.com.au:20150613:12345",
            "version":
            "1",
            "place": [{
                "code": "NSW",
                "name": "New South Wales"
            }],
            "pubstatus":
            "usable",
            "body_html":
            "The story body<p>call helpline 999 if you are planning to quit smoking</p>",
            "type":
            "text",
            "subject": [{
                "code": "02011001",
                "name": "international court or tribunal"
            }, {
                "code": "02011002",
                "name": "extradition"
            }],
            "service": [{
                "code": "a"
            }],
            "source":
            "AAP",
            "headline":
            "This is a test headline",
            "byline":
            "joe",
            "urgency":
            2,
            "priority":
            1,
            "embargoed":
            embargo_ts.isoformat(),
            "profile":
            "snap",
            "slugline":
            "slugline",
            "description_text":
            "sample abstract",
            "description_html":
            "<p>sample <b>abstract</b></p>",
            'keywords': ['traffic'],
            'organisation': [{
                'name': 'YANCOAL AUSTRALIA LIMITED',
                'rel': 'Securities Identifier',
                'symbols': [{
                    'ticker': 'YAL',
                    'exchange': 'ASX'
                }]
            }],
            'genre': [{
                'name': 'Article',
                'code': 'article'
            }],
            'signal': [{
                'name': 'Content Warning',
                'code': 'cwarn',
                'scheme': 'http://cv.iptc.org/newscodes/signal/'
            }],
            'extra': {
                'foo': 'test'
            },
            'charcount':
            67,
            'wordcount':
            13,
            'readtime':
            0,
            'products': [{
                'code': 1,
                'name': 'p-1'
            }]
        }
        self.assertEqual(json.loads(doc), expected)
        article['urgency'] = 1
        seq, doc = self.formatter.format(article,
                                         {'name': 'Test Subscriber'})[0]
        expected = {
            "guid":
            "tag:aap.com.au:20150613:12345",
            "version":
            "1",
            "place": [{
                "code": "NSW",
                "name": "New South Wales"
            }],
            "pubstatus":
            "usable",
            "body_html":
            "The story body<p>call helpline 999 if you are planning to quit smoking</p>",
            "type":
            "text",
            "subject": [{
                "code": "02011001",
                "name": "international court or tribunal"
            }, {
                "code": "02011002",
                "name": "extradition"
            }],
            "service": [{
                "code": "a"
            }],
            "source":
            "AAP",
            "headline":
            "This is a test headline",
            "byline":
            "joe",
            "urgency":
            1,
            "priority":
            1,
            "embargoed":
            embargo_ts.isoformat(),
            "profile":
            "snap",
            "slugline":
            "slugline",
            "description_text":
            "sample abstract",
            "description_html":
            "<p>sample <b>abstract</b></p>",
            'keywords': ['traffic'],
            'organisation': [{
                'name': 'YANCOAL AUSTRALIA LIMITED',
                'rel': 'Securities Identifier',
                'symbols': [{
                    'ticker': 'YAL',
                    'exchange': 'ASX'
                }]
            }],
            'genre': [{
                'name': 'Article',
                'code': 'article'
            }],
            'signal': [{
                'name': 'Content Warning',
                'code': 'cwarn',
                'scheme': 'http://cv.iptc.org/newscodes/signal/'
            }],
            'extra': {
                'foo': 'test'
            },
            'charcount':
            67,
            'wordcount':
            13,
            'readtime':
            0,
            'products': []
        }
        self.assertEqual(json.loads(doc), expected)

    def test_planning_data(self):
        planning_assignments.init_app(self.app)
        planning_planning.init_app(self.app)

        assignments = [{
            'coverage_item': 'urn:coverage-id',
            'planning_item': 'urn:planning-id'
        }]
        self.app.data.insert('assignments', assignments)

        article = {
            '_id': 'tag:aap.com.au:20150613:12345',
            'guid': 'tag:aap.com.au:20150613:12345',
            'type': 'text',
            'version': 1,
            'assignment_id': assignments[0]['_id'],
        }

        seq, doc = self.formatter.format(article,
                                         {'name': 'Test Subscriber'})[0]
        data = json.loads(doc)

        self.assertEqual('urn:planning-id', data['planning_id'])
        self.assertEqual('urn:coverage-id', data['coverage_id'])

    def test_picture_formatter(self):
        article = {
            "guid":
            "20150723001158606583",
            "_current_version":
            1,
            "slugline":
            "AMAZING PICTURE",
            "original_source":
            "AAP",
            "renditions": {
                "viewImage": {
                    "width": 640,
                    "href":
                    "http://localhost:5000/api/upload/55b032041d41c8d278d21b6f/raw?_schema=http",
                    "mimetype": "image/jpeg",
                    "height": 401,
                },
                "original": {
                    "href":
                    "https://one-api.aap.com.au/api/v3/Assets/20150723001158606583/Original/download",
                    "mimetype": "image/jpeg",
                },
            },
            "byline":
            "MICKEY MOUSE",
            "headline":
            "AMAZING PICTURE",
            "versioncreated":
            "2015-07-23T00:15:00.000Z",
            "ednote":
            "TEST ONLY",
            "type":
            "picture",
            "pubstatus":
            "usable",
            "source":
            "AAP",
            "description":
            "The most amazing picture you will ever see",
            "guid":
            "20150723001158606583",
            "body_footer":
            "<p>call helpline 999 if you are planning to quit smoking</p>",
        }
        seq, doc = self.formatter.format(article,
                                         {"name": "Test Subscriber"})[0]
        expected = {
            "byline":
            "MICKEY MOUSE",
            "renditions": {
                "original": {
                    "href":
                    "https://one-api.aap.com.au/api/v3/Assets/20150723001158606583/Original/download",
                    "mimetype": "image/jpeg",
                },
                "viewImage": {
                    "href":
                    "http://localhost:5000/api/upload/55b032041d41c8d278d21b6f/raw?_schema=http",
                    "mimetype": "image/jpeg",
                    "width": 640,
                    "height": 401,
                }
            },
            "headline":
            "AMAZING PICTURE",
            "pubstatus":
            "usable",
            "version":
            "1",
            "versioncreated":
            "2015-07-23T00:15:00.000Z",
            "guid":
            "20150723001158606583",
            "description_html":
            "The most amazing picture you will ever see<p>call helpline 999 if you are planning to "
            "quit smoking</p>",
            "type":
            "picture",
            "priority":
            5,
            "slugline":
            "AMAZING PICTURE",
            "ednote":
            "TEST ONLY",
            "source":
            "AAP",
            "products": [],
        }
        self.assertEqual(expected, json.loads(doc))
        self.assertIn('viewImage', json.loads(doc).get('renditions'))

    def test_auto_published_item(self):
        article = {
            "guid":
            "foo",
            "_current_version":
            1,
            "slugline":
            "AMAZING PICTURE",
            "original_source":
            "AAP",
            "byline":
            "MICKEY MOUSE",
            "headline":
            "AMAZING PICTURE",
            "versioncreated":
            "2015-07-23T00:15:00.000Z",
            "ednote":
            "TEST ONLY",
            "type":
            "picture",
            "pubstatus":
            "usable",
            "source":
            "AAP",
            "description":
            "The most amazing picture you will ever see",
            "body_footer":
            "<p>call helpline 999 if you are planning to quit smoking</p>",
        }
        _, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        processed = json.loads(doc)
        self.assertEqual(processed['guid'], 'foo')
        article['ingest_id'] = 'bar'
        article['ingest_version'] = '7'
        _, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        processed = json.loads(doc)
        self.assertEqual(processed['guid'], 'foo')
        article['auto_publish'] = True
        _, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        processed = json.loads(doc)
        self.assertEqual(processed['guid'], 'bar')
        self.assertEqual(processed['version'], '7')
예제 #3
0
class PublishService(BaseService):
    """A service for publishing to the content api.

    Serves mainly as a proxy to the data layer.
    """

    formatter = NewsroomNinjsFormatter()
    subscriber: Dict[str, Dict] = {"config": {}}

    def publish(self, item, subscribers=None):
        """Publish an item to content api.

        This must be enabled via ``PUBLISH_TO_CONTENT_API`` setting.

        :param item: item to publish
        """

        if subscribers is None:
            subscribers = []

        if not self._filter_item(item):
            item = EnqueueService.filter_document(item)
            item = remove_metadata_for_publish(item)
            doc = self.formatter._transform_to_ninjs(item, self.subscriber)
            now = utcnow()
            doc.setdefault("firstcreated", now)
            doc.setdefault("versioncreated", now)
            doc.setdefault(config.VERSION, item.get(config.VERSION, 1))
            for _, assoc in doc.get(ASSOCIATIONS, {}).items():
                if assoc:
                    assoc.setdefault("subscribers", [
                        str(subscriber[config.ID_FIELD])
                        for subscriber in subscribers
                    ])
            doc["subscribers"] = [str(sub["_id"]) for sub in subscribers]
            if "evolvedfrom" in doc:
                parent_item = self.find_one(req=None, _id=doc["evolvedfrom"])
                if parent_item:
                    doc["ancestors"] = copy(parent_item.get("ancestors", []))
                    doc["ancestors"].append(doc["evolvedfrom"])
                    doc["bookmarks"] = parent_item.get("bookmarks", [])
                else:
                    logger.warning(
                        "Failed to find evolvedfrom item '{}' for '{}'".format(
                            doc["evolvedfrom"], doc["guid"]))

            self._assign_associations(item, doc)
            logger.info("publishing %s to %s" % (doc["guid"], subscribers))
            _id = self._create_doc(doc)
            if "evolvedfrom" in doc and parent_item:
                self.system_update(parent_item["_id"], {"nextversion": _id},
                                   parent_item)
            return _id
        else:
            return None

    def create(self, docs, **kwargs):
        ids = []
        for doc in docs:
            ids.append(self._create_doc(doc, **kwargs))
        return ids

    def _create_doc(self, doc, **kwargs):
        """Create a new item or update existing."""
        item = copy(doc)
        item.setdefault("_id", item.get("guid"))
        _id = item[config.ID_FIELD] = item.pop("guid")

        # merging the existing and new subscribers
        original = self.find_one(req=None, _id=_id)
        if original:
            item["subscribers"] = list(
                set(original.get("subscribers", []))
                | set(item.get("subscribers", [])))

        self._process_associations(item, original)
        self._create_version_doc(item)
        if original:
            self.update(_id, item, original)
            return _id
        else:
            return super().create([item], **kwargs)[0]

    def _create_version_doc(self, item):
        """
        Store the item in the item version collection
        :param item:
        :return:
        """
        version_item = copy(item)
        version_item["_id_document"] = version_item.pop("_id")
        get_resource_service("items_versions").create([version_item])
        # if the update is a cancel we need to cancel all versions
        if item.get("pubstatus", "") == "canceled":
            self._cancel_versions(item.get("_id"))

    def _cancel_versions(self, doc_id):
        """
        Given an id of a document set the pubstatus to canceled for all versions
        :param doc_id:
        :return:
        """
        query = {"_id_document": doc_id}
        update = {"pubstatus": "canceled"}
        for item in get_resource_service("items_versions").get_from_mongo(
                req=None, lookup=query):
            if item.get("pubstatus") != "canceled":
                get_resource_service("items_versions").update(
                    item["_id"], update, item)

    def _filter_item(self, item):
        """
        Filter the item out if it matches any API Block filter conditions
        :param item:
        :return: True of the item is blocked, False if it is OK to publish it on the API.
        """
        # Get the API blocking Filters
        req = ParsedRequest()
        filter_conditions = list(
            get_resource_service("content_filters").get(
                req=req, lookup={"api_block": True}))

        # No API blocking filters
        if not filter_conditions:
            return False

        filter_service = get_resource_service("content_filters")
        for fc in filter_conditions:
            if filter_service.does_match(fc, item):
                logger.info("API Filter block {} matched for item {}.".format(
                    fc, item.get(config.ID_FIELD)))
                return True

        return False

    def _assign_associations(self, item, doc):
        """Assign Associations to published item

        :param dict item: item being published
        :param dit doc: ninjs documents
        """
        for assoc, assoc_item in (item.get("associations") or {}).items():
            if not assoc_item:
                continue
            doc.get("associations", {}).get(assoc)["subscribers"] = list(
                map(str,
                    assoc_item.get("subscribers") or []))

    def _process_associations(self, updates, original):
        """Update associations using existing published item and ensure that associated item subscribers
        are equal or subset of the parent subscribers.
        :param updates:
        :param original:
        :return:
        """
        subscribers = updates.get("subscribers") or []
        for assoc, update_assoc in (updates.get("associations") or {}).items():
            if not update_assoc:
                continue

            if original:
                original_assoc = (original.get("associations")
                                  or {}).get(assoc)

                if original_assoc and original_assoc.get(
                        config.ID_FIELD) == update_assoc.get(config.ID_FIELD):
                    update_assoc["subscribers"] = list(
                        set(original_assoc.get("subscribers") or [])
                        | set(update_assoc.get("subscribers") or []))

            update_assoc["subscribers"] = list(
                set(update_assoc["subscribers"]) & set(subscribers))
class NewsroomNinjsFormatterTest(TestCase):
    def setUp(self):
        self.formatter = NewsroomNinjsFormatter()
        init_app(self.app)
        self.maxDiff = None

    def test_products(self):
        self.app.data.insert(
            "content_filters",
            [{"_id": 3, "content_filter": [{"expression": {"pf": [1], "fc": [2]}}], "name": "soccer-only3"}],
        )
        self.app.data.insert(
            "filter_conditions",
            [{"_id": 1, "field": "headline", "operator": "like", "value": "test", "name": "test-1"}],
        )
        self.app.data.insert(
            "filter_conditions", [{"_id": 2, "field": "urgency", "operator": "in", "value": "2", "name": "test-2"}]
        )
        self.app.data.insert(
            "products",
            [
                {
                    "_id": 1,
                    "content_filter": {"filter_id": 3, "filter_type": "permitting"},
                    "name": "p-1",
                    "product_type": "api",
                }
            ],
        )
        self.app.data.insert(
            "vocabularies",
            [
                {
                    "_id": "locators",
                    "display_name": "Locators",
                    "type": "unmanageable",
                    "unique_field": "qcode",
                    "items": [
                        {
                            "is_active": True,
                            "name": "NSW",
                            "qcode": "NSW",
                            "state": "New South Wales",
                            "country": "Australia",
                            "world_region": "Oceania",
                            "group": "Australia",
                        },
                    ],
                }
            ],
        )
        embargo_ts = utcnow() + timedelta(days=2)
        article = {
            "_id": "tag:aap.com.au:20150613:12345",
            "guid": "tag:aap.com.au:20150613:12345",
            "_current_version": 1,
            "anpa_category": [{"qcode": "a"}],
            "source": "AAP",
            "headline": "This is a test headline",
            "byline": "joe",
            "slugline": "slugline",
            "subject": [
                {"qcode": "02011001", "name": "international court or tribunal", "parent": None},
                {"qcode": "02011002", "name": "extradition"},
            ],
            "anpa_take_key": "take_key",
            "unique_id": "1",
            "body_html": "The story body",
            "type": "text",
            "word_count": "1",
            "priority": 1,
            "profile": "snap",
            "state": "published",
            "urgency": 2,
            "pubstatus": "usable",
            "creditline": "sample creditline",
            "keywords": ["traffic"],
            "abstract": "<p>sample <b>abstract</b></p>",
            "place": [{"name": "NSW", "qcode": "NSW"}],
            "embargo": embargo_ts,
            "body_footer": "<p>call helpline 999 if you are planning to quit smoking</p>",
            "company_codes": [{"name": "YANCOAL AUSTRALIA LIMITED", "qcode": "YAL", "security_exchange": "ASX"}],
            "genre": [{"name": "Article", "qcode": "article"}],
            "flags": {"marked_for_legal": True},
            "extra": {"foo": "test"},
            "operation": "publish",
        }
        seq, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        expected = {
            "guid": "tag:aap.com.au:20150613:12345",
            "version": "1",
            "place": [{"code": "NSW", "name": "New South Wales"}],
            "pubstatus": "usable",
            "body_html": "The story body<p>call helpline 999 if you are planning to quit smoking</p>",
            "type": "text",
            "subject": [
                {"code": "02011001", "name": "international court or tribunal"},
                {"code": "02011002", "name": "extradition"},
            ],
            "service": [{"code": "a"}],
            "source": "AAP",
            "headline": "This is a test headline",
            "byline": "joe",
            "urgency": 2,
            "priority": 1,
            "embargoed": embargo_ts.isoformat(),
            "profile": "snap",
            "slugline": "slugline",
            "description_text": "sample abstract",
            "description_html": "<p>sample <b>abstract</b></p>",
            "keywords": ["traffic"],
            "organisation": [
                {
                    "name": "YANCOAL AUSTRALIA LIMITED",
                    "rel": "Securities Identifier",
                    "symbols": [{"ticker": "YAL", "exchange": "ASX"}],
                }
            ],
            "genre": [{"name": "Article", "code": "article"}],
            "signal": [{"name": "Content Warning", "code": "cwarn", "scheme": "http://cv.iptc.org/newscodes/signal/"}],
            "extra": {"foo": "test"},
            "charcount": 67,
            "wordcount": 13,
            "readtime": 0,
            "products": [{"code": 1, "name": "p-1"}],
        }
        self.assertEqual(json.loads(doc), expected)
        article["urgency"] = 1
        seq, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        expected = {
            "guid": "tag:aap.com.au:20150613:12345",
            "version": "1",
            "place": [{"code": "NSW", "name": "New South Wales"}],
            "pubstatus": "usable",
            "body_html": "The story body<p>call helpline 999 if you are planning to quit smoking</p>",
            "type": "text",
            "subject": [
                {"code": "02011001", "name": "international court or tribunal"},
                {"code": "02011002", "name": "extradition"},
            ],
            "service": [{"code": "a"}],
            "source": "AAP",
            "headline": "This is a test headline",
            "byline": "joe",
            "urgency": 1,
            "priority": 1,
            "embargoed": embargo_ts.isoformat(),
            "profile": "snap",
            "slugline": "slugline",
            "description_text": "sample abstract",
            "description_html": "<p>sample <b>abstract</b></p>",
            "keywords": ["traffic"],
            "organisation": [
                {
                    "name": "YANCOAL AUSTRALIA LIMITED",
                    "rel": "Securities Identifier",
                    "symbols": [{"ticker": "YAL", "exchange": "ASX"}],
                }
            ],
            "genre": [{"name": "Article", "code": "article"}],
            "signal": [{"name": "Content Warning", "code": "cwarn", "scheme": "http://cv.iptc.org/newscodes/signal/"}],
            "extra": {"foo": "test"},
            "charcount": 67,
            "wordcount": 13,
            "readtime": 0,
            "products": [],
        }
        self.assertEqual(json.loads(doc), expected)

    def test_planning_data(self):
        planning_assignments.init_app(self.app)
        planning_planning.init_app(self.app)

        assignments = [{"coverage_item": "urn:coverage-id", "planning_item": "urn:planning-id"}]
        self.app.data.insert("assignments", assignments)

        article = {
            "_id": "tag:aap.com.au:20150613:12345",
            "guid": "tag:aap.com.au:20150613:12345",
            "type": "text",
            "version": 1,
            "assignment_id": assignments[0]["_id"],
        }

        seq, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        data = json.loads(doc)

        self.assertEqual("urn:planning-id", data["planning_id"])
        self.assertEqual("urn:coverage-id", data["coverage_id"])

    def test_picture_formatter(self):
        article = {
            "guid": "20150723001158606583",
            "_current_version": 1,
            "slugline": "AMAZING PICTURE",
            "original_source": "AAP",
            "renditions": {
                "viewImage": {
                    "width": 640,
                    "href": "http://localhost:5000/api/upload/55b032041d41c8d278d21b6f/raw?_schema=http",
                    "mimetype": "image/jpeg",
                    "height": 401,
                },
                "original": {
                    "href": "https://one-api.aap.com.au/api/v3/Assets/20150723001158606583/Original/download",
                    "mimetype": "image/jpeg",
                },
            },
            "byline": "MICKEY MOUSE",
            "headline": "AMAZING PICTURE",
            "versioncreated": "2015-07-23T00:15:00.000Z",
            "ednote": "TEST ONLY",
            "type": "picture",
            "pubstatus": "usable",
            "source": "AAP",
            "description": "The most amazing picture you will ever see",
            "guid": "20150723001158606583",
            "body_footer": "<p>call helpline 999 if you are planning to quit smoking</p>",
        }
        seq, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        expected = {
            "byline": "MICKEY MOUSE",
            "renditions": {
                "original": {
                    "href": "https://one-api.aap.com.au/api/v3/Assets/20150723001158606583/Original/download",
                    "mimetype": "image/jpeg",
                },
                "viewImage": {
                    "href": "http://localhost:5000/api/upload/55b032041d41c8d278d21b6f/raw?_schema=http",
                    "mimetype": "image/jpeg",
                    "width": 640,
                    "height": 401,
                },
            },
            "headline": "AMAZING PICTURE",
            "pubstatus": "usable",
            "version": "1",
            "versioncreated": "2015-07-23T00:15:00.000Z",
            "guid": "20150723001158606583",
            "description_html": "The most amazing picture you will ever see<p>call helpline 999 if you are planning to "
            "quit smoking</p>",
            "type": "picture",
            "priority": 5,
            "slugline": "AMAZING PICTURE",
            "ednote": "TEST ONLY",
            "source": "AAP",
            "products": [],
        }
        self.assertEqual(expected, json.loads(doc))
        self.assertIn("viewImage", json.loads(doc).get("renditions"))

    def test_auto_published_item(self):
        article = {
            "guid": "foo",
            "_current_version": 1,
            "slugline": "AMAZING PICTURE",
            "original_source": "AAP",
            "byline": "MICKEY MOUSE",
            "headline": "AMAZING PICTURE",
            "versioncreated": "2015-07-23T00:15:00.000Z",
            "ednote": "TEST ONLY",
            "type": "picture",
            "pubstatus": "usable",
            "source": "AAP",
            "description": "The most amazing picture you will ever see",
            "body_footer": "<p>call helpline 999 if you are planning to quit smoking</p>",
        }
        _, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        processed = json.loads(doc)
        self.assertEqual(processed["guid"], "foo")
        article["ingest_id"] = "bar"
        article["ingest_version"] = "7"
        _, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        processed = json.loads(doc)
        self.assertEqual(processed["guid"], "foo")
        article["auto_publish"] = True
        _, doc = self.formatter.format(article, {"name": "Test Subscriber"})[0]
        processed = json.loads(doc)
        self.assertEqual(processed["guid"], "bar")
        self.assertEqual(processed["version"], "7")
 def setUp(self):
     self.formatter = NewsroomNinjsFormatter()
     init_app(self.app)
     self.maxDiff = None
예제 #6
0
class NinjsFormatterTest(TestCase):
    def setUp(self):
        self.formatter = NewsroomNinjsFormatter()
        init_app(self.app)
        self.maxDiff = None

    def test_products(self):
        self.app.data.insert('content_filters',
                             [{"_id": 3,
                               "content_filter": [{"expression": {"pf": [1], "fc": [2]}}],
                               "name": "soccer-only3"}])
        self.app.data.insert('filter_conditions',
                             [{'_id': 1,
                               'field': 'headline',
                               'operator': 'like',
                               'value': 'test',
                               'name': 'test-1'}])
        self.app.data.insert('filter_conditions',
                             [{'_id': 2,
                               'field': 'urgency',
                               'operator': 'in',
                               'value': '2',
                               'name': 'test-2'}])
        self.app.data.insert('products',
                             [{"_id": 1,
                               "content_filter": {"filter_id": 3, "filter_type": "permitting"},
                               "name": "p-1", "product_type": "api"}])
        self.app.data.insert('vocabularies', [
            {
                "_id": "locators",
                "display_name": "Locators",
                "type": "unmanageable",
                "unique_field": "qcode",
                "items": [
                    {"is_active": True, "name": "NSW", "qcode": "NSW", "state": "New South Wales",
                     "country": "Australia", "world_region": "Oceania", "group": "Australia"},
                ],
            }
        ])
        embargo_ts = (utcnow() + timedelta(days=2))
        article = {
            '_id': 'tag:aap.com.au:20150613:12345',
            'guid': 'tag:aap.com.au:20150613:12345',
            '_current_version': 1,
            'anpa_category': [{'qcode': 'a'}],
            'source': 'AAP',
            'headline': 'This is a test headline',
            'byline': 'joe',
            'slugline': 'slugline',
            'subject': [{'qcode': '02011001', 'name': 'international court or tribunal', 'parent': None},
                        {'qcode': '02011002', 'name': 'extradition'}],
            'anpa_take_key': 'take_key',
            'unique_id': '1',
            'body_html': 'The story body',
            'type': 'text',
            'word_count': '1',
            'priority': 1,
            'profile': 'snap',
            'state': 'published',
            'urgency': 2,
            'pubstatus': 'usable',
            'creditline': 'sample creditline',
            'keywords': ['traffic'],
            'abstract': '<p>sample <b>abstract</b></p>',
            'place': [{'name': 'NSW', 'qcode': 'NSW'}],
            'embargo': embargo_ts,
            'body_footer': '<p>call helpline 999 if you are planning to quit smoking</p>',
            'company_codes': [{'name': 'YANCOAL AUSTRALIA LIMITED', 'qcode': 'YAL', 'security_exchange': 'ASX'}],
            'genre': [{'name': 'Article', 'qcode': 'article'}],
            'flags': {'marked_for_legal': True},
            'extra': {'foo': 'test'},
        }
        seq, doc = self.formatter.format(article, {'name': 'Test Subscriber'})[0]
        expected = {
            "guid": "tag:aap.com.au:20150613:12345",
            "version": "1",
            "place": [{"code": "NSW", "name": "New South Wales"}],
            "pubstatus": "usable",
            "body_html": "The story body<p>call helpline 999 if you are planning to quit smoking</p>",
            "type": "text",
            "subject": [{"code": "02011001", "name": "international court or tribunal"},
                        {"code": "02011002", "name": "extradition"}],
            "service": [{"code": "a"}],
            "source": "AAP",
            "headline": "This is a test headline",
            "byline": "joe",
            "urgency": 2,
            "priority": 1,
            "embargoed": embargo_ts.isoformat(),
            "profile": "snap",
            "slugline": "slugline",
            "description_text": "sample abstract",
            "description_html": "<p>sample <b>abstract</b></p>",
            'keywords': ['traffic'],
            'organisation': [{'name': 'YANCOAL AUSTRALIA LIMITED', 'rel': 'Securities Identifier',
                              'symbols': [{'ticker': 'YAL', 'exchange': 'ASX'}]}],
            'genre': [{'name': 'Article', 'code': 'article'}],
            'signal': [{'name': 'Content Warning', 'code': 'cwarn', 'scheme': 'http://cv.iptc.org/newscodes/signal/'}],
            'extra': {'foo': 'test'},
            'charcount': 67,
            'wordcount': 13,
            'readtime': 0,
            'products': [{'code': 1, 'name': 'p-1'}]
        }
        self.assertEqual(json.loads(doc), expected)
        article['urgency'] = 1
        seq, doc = self.formatter.format(article, {'name': 'Test Subscriber'})[0]
        expected = {
            "guid": "tag:aap.com.au:20150613:12345",
            "version": "1",
            "place": [{"code": "NSW", "name": "New South Wales"}],
            "pubstatus": "usable",
            "body_html": "The story body<p>call helpline 999 if you are planning to quit smoking</p>",
            "type": "text",
            "subject": [{"code": "02011001", "name": "international court or tribunal"},
                        {"code": "02011002", "name": "extradition"}],
            "service": [{"code": "a"}],
            "source": "AAP",
            "headline": "This is a test headline",
            "byline": "joe",
            "urgency": 1,
            "priority": 1,
            "embargoed": embargo_ts.isoformat(),
            "profile": "snap",
            "slugline": "slugline",
            "description_text": "sample abstract",
            "description_html": "<p>sample <b>abstract</b></p>",
            'keywords': ['traffic'],
            'organisation': [{'name': 'YANCOAL AUSTRALIA LIMITED', 'rel': 'Securities Identifier',
                              'symbols': [{'ticker': 'YAL', 'exchange': 'ASX'}]}],
            'genre': [{'name': 'Article', 'code': 'article'}],
            'signal': [{'name': 'Content Warning', 'code': 'cwarn', 'scheme': 'http://cv.iptc.org/newscodes/signal/'}],
            'extra': {'foo': 'test'},
            'charcount': 67,
            'wordcount': 13,
            'readtime': 0,
            'products': []
        }
        self.assertEqual(json.loads(doc), expected)