Я хочу настроить систему опроса каналов xml, которая будет загружать XML-канал из заданного URL каждый час и определять, изменился ли канал. Если это так, ему нужно будет сделать несколько вещей.
Как я могу эффективно это сделать? Подача, которую я бы вытащил, будет иметь тысячи элементов внутри, и каждый элемент может иметь довольно много данных в нем.
Я хочу иметь возможность обнаруживать любые новые данные / элемент и сохранять их в базе данных.
Я хочу иметь возможность обнаруживать любые измененные данные / элемент и соответственно обновлять базу данных.
Я хочу иметь возможность обнаруживать любые удаленные данные / элемент и соответственно обновлять базу данных.
Порядок элементов не имеет значения для меня, поэтому, если порядок меняется, но ничего не делает, мы можем сказать, что каналы идентичны.
Я видел, как несколько человек упоминают хэширование элементов и всего фида для сравнения с предыдущим загруженным. Если есть много предметов, это может занять много времени.
Будет ли простой способ сделать diff для последнего загруженного фида и нового, чтобы затем удалить все одинаковые элементы? И, может быть, затем перейдите по пунктам, которые остались и выполните сравнение?
Я не уверен, какой будет правильный подход. Любые предложения будут ценны.
Примером подобной подачи я бы потянул бы:
<properties> <property> <location> <unit-number>301</unit-number> <street-address>123 Main St</street-address> <city-name>San Francisco</city-name> <zipcode>94123</zipcode> <county>San Francisco</county> <state-code>California</state-code> <street-intersection>Broadway</street-intersection> <parcel-id>359-02-4158</parcel-id> <building-name>The Avalon</building-name> <subdivision></subdivision> <neighborhood-name>Marina</neighborhood-name> <neighborhood-description>The Marina is a neighborhood on the Northern part of San Francisco</neighborhood-description> <elevation>10</elevation> <longitude>-70.1200</longitude> <latitude>30.0000</latitude> <geocode-type>exact</geocode-type> <display-address>yes</display-address> <directions>Take 101 North to Lombard St. Make a left on Lombard and 3rd right onto Main. 123 is at the end of the block on the right. </directions> </location> <details> <listing-title>A great deal in the Marina</listing-title> <price>725000</price> <year-built>1928</year-built> <num-bedrooms>3</num-bedrooms> <num-full-bathrooms>2</num-full-bathrooms> <num-half-bathrooms>1</num-half-bathrooms> <num-bathrooms></num-bathrooms> <lot-size>0.25</lot-size> <living-area-square-feet>1720</living-area-square-feet> <date-listed>2010-06-20</date-listed> <date-available></date-available> <date-sold></date-sold> <sale-price></sale-price> <property-type>condo</property-type> <description>Newly remodeled condo in great location.</description> <mlsId>582649</mlsId> <mlsName>SFAR</mlsName> <provider-listingid>258136842</provider-listingid> </details> <landing-page> <lp-url>http://www.BrokerRealty.com/listing?id=123456&source=Trulia</lp-url> </landing-page> <listing-type>resale</listing-type> <status>for sale</status> <foreclosure-status></foreclosure-status> <site> <site-url>http://www.BrokerRealty.com</site-url> <site-name>Broker Realty</site-name> </site>
и т.д..
Будет ли простой способ сделать diff для последнего загруженного фида и нового, чтобы затем удалить все одинаковые элементы?
Конечно, на самом деле это должно быть довольно легко. Похоже, что это недвижимость, правда? Если это так, имя поставщика MLS и идентификатор, который они выдают для листинга, образуют уникальный ключ:
<details> <!-- ... --> <mlsId>582649</mlsId> <mlsName>SFAR</mlsName> <provider-listingid>258136842</provider-listingid> </details>
Теперь, когда вы можете однозначно идентифицировать каждый список, должно быть довольно тривиально решить, как вы обнаружите изменения. Я лично манипулирую XML в многомерном ассоциативном массиве, сортирую каждый уровень по имени ключа, затем сериализую его и запускаю через хэш-процедуру (скажем, md5), потому что это очень привлекательное sloppy-but-it-works эффект. Фактически, у вас уже была эта идея, вроде:
Я видел, как несколько человек упоминают хэширование элементов и всего фида для сравнения с предыдущим загруженным. Если есть много предметов, это может занять много времени.
Хешируя каждую уникальную запись в документе, вы избегаете повторной передачи всей вещи при изменении одной записи. Вставьте хеш-запись в каждом остатке данных в своей базе данных с информацией, составляющей уникальный ключ. Когда хеш изменяется, XML изменился, и его стоит повторно импортировать.
И снова, когда у вас есть этот уникальный ключ, удивительно легко обнаружить новые списки. В базе данных нет соответствующего ключа? Импортировать.
Аналогично, удивительно легко обнаружить удаленные записи. Ключи в базе данных, но не в XML? Может быть, он должен быть заряжен.