feature: movie description
parent
9aa0278ab0
commit
0520120ccf
|
@ -75,7 +75,7 @@ class WikidataMovieApi implements MovieApi {
|
|||
final start = i * batchSize;
|
||||
final end = min((i + 1) * batchSize, movieIds.length);
|
||||
var response = await _wikidataApi.get(
|
||||
"&action=wbgetentities&format=json&props=labels|claims&ids=${movieIds.sublist(start, end).join("|")}");
|
||||
"&action=wbgetentities&format=json&props=labels|claims|sitelinks/urls&ids=${movieIds.sublist(start, end).join("|")}");
|
||||
Map<String, dynamic> result = jsonDecode(response.body);
|
||||
Map<String, dynamic> batchEntities = result["entities"];
|
||||
entities.addAll(batchEntities);
|
||||
|
@ -94,6 +94,12 @@ class WikidataMovieApi implements MovieApi {
|
|||
// they will be retrieved from the cache in fromWikidataEntity
|
||||
await _getLabelsForEntities(allCountryAndGenreIds);
|
||||
|
||||
// Get wikipedia explaintexts
|
||||
Iterable<String> allWikipediaTitles =
|
||||
selectInJson<String>(entities, "*.sitelinks.enwiki.url")
|
||||
.map((url) => url.split("/").last);
|
||||
await _getWikipediaExplainTextForTitles(allWikipediaTitles.toList());
|
||||
|
||||
return movieIds
|
||||
.map((id) => WikidataMovieData.fromWikidataEntity(id, entities[id]))
|
||||
.toList();
|
||||
|
@ -142,6 +148,13 @@ class WikidataMovieData extends MovieData {
|
|||
String title =
|
||||
selectInJson<String>(entity, "labels.en.value").firstOrNull ??
|
||||
selectInJson<String>(entity, "labels.*.value").first;
|
||||
String? wikipediaTitle = selectInJson(entity, "sitelinks.enwiki.url")
|
||||
.firstOrNull
|
||||
?.split("/")
|
||||
.last;
|
||||
String? description = wikipediaTitle != null
|
||||
? _getCachedWikipediaExplainTextFotTitle(wikipediaTitle)
|
||||
: null;
|
||||
Map<String, dynamic> claims = entity["claims"];
|
||||
List<TitleInLanguage>? titles = selectInJson(
|
||||
claims, "${WikidataProperties.title}.*.mainsnak.datavalue.value")
|
||||
|
@ -167,6 +180,7 @@ class WikidataMovieData extends MovieData {
|
|||
DateTime.now(), DatePrecision.decade, "unknown location"),
|
||||
entityId);
|
||||
movie.setDetails(
|
||||
description: description,
|
||||
titles: titles,
|
||||
releaseDates: releaseDates,
|
||||
genres: genres,
|
||||
|
@ -267,3 +281,44 @@ Future<Map<String, String>> _getLabelsForEntities(
|
|||
String _getCachedLabelForEntity(String entityId) {
|
||||
return _labelCache[entityId] ?? entityId;
|
||||
}
|
||||
|
||||
ApiManager _wikipediaApi =
|
||||
ApiManager("https://en.wikipedia.org/w/api.php?format=json&origin=*");
|
||||
Map<String, String> _wikipediaExplainTextCache = {};
|
||||
Future<Map<String, String>> _getWikipediaExplainTextForTitles(
|
||||
List<String> pageTitles) async {
|
||||
const batchSize = 50;
|
||||
Map<String, String> explainTexts = {};
|
||||
for (int i = pageTitles.length - 1; i >= 0; i--) {
|
||||
if (_labelCache.containsKey(pageTitles[i])) {
|
||||
explainTexts[pageTitles[i]] = _labelCache[pageTitles[i]]!;
|
||||
pageTitles.removeAt(i);
|
||||
}
|
||||
}
|
||||
for (int i = 0; i < (pageTitles.length / batchSize).ceil(); i++) {
|
||||
final start = i * batchSize;
|
||||
final end = min((i + 1) * batchSize, pageTitles.length);
|
||||
Response response = await _wikipediaApi.get(
|
||||
"&action=query&prop=extracts&exintro&explaintext&redirects=1&titles=${pageTitles.sublist(start, end).join("|")}");
|
||||
Map<String, dynamic> result = jsonDecode(response.body);
|
||||
List<dynamic> normalize = result["query"]["normalized"];
|
||||
Map<String, dynamic> batchPages = result["query"]["pages"];
|
||||
for (String pageId in batchPages.keys) {
|
||||
String pageTitle = batchPages[pageId]["title"];
|
||||
String originalTitle = normalize
|
||||
.where((element) => element["to"] == pageTitle)
|
||||
.firstOrNull?["from"] ??
|
||||
pageTitle;
|
||||
String? explainText = batchPages[pageId]["extract"];
|
||||
if (explainText != null) {
|
||||
_wikipediaExplainTextCache[originalTitle] =
|
||||
explainTexts[originalTitle] = explainText;
|
||||
}
|
||||
}
|
||||
}
|
||||
return explainTexts;
|
||||
}
|
||||
|
||||
String? _getCachedWikipediaExplainTextFotTitle(String title) {
|
||||
return _wikipediaExplainTextCache[title];
|
||||
}
|
||||
|
|
|
@ -7,6 +7,7 @@ class MovieData extends ChangeNotifier {
|
|||
bool _bookmarked = false;
|
||||
|
||||
bool _hasDetails = false;
|
||||
String? _description;
|
||||
List<DateWithPrecisionAndCountry>? _releaseDates;
|
||||
List<String>? _genres;
|
||||
List<TitleInLanguage>? _titles;
|
||||
|
@ -25,6 +26,10 @@ class MovieData extends ChangeNotifier {
|
|||
return _bookmarked;
|
||||
}
|
||||
|
||||
get description {
|
||||
return _description;
|
||||
}
|
||||
|
||||
List<DateWithPrecisionAndCountry>? get releaseDates {
|
||||
return _releaseDates;
|
||||
}
|
||||
|
@ -47,6 +52,7 @@ class MovieData extends ChangeNotifier {
|
|||
setDetails(
|
||||
title: movie.title,
|
||||
releaseDate: movie.releaseDate,
|
||||
description: movie.description,
|
||||
releaseDates: movie.releaseDates,
|
||||
genres: movie.genres,
|
||||
titles: movie.titles);
|
||||
|
@ -56,6 +62,7 @@ class MovieData extends ChangeNotifier {
|
|||
{String? title,
|
||||
DateWithPrecisionAndCountry? releaseDate,
|
||||
bool? bookmarked,
|
||||
String? description,
|
||||
List<DateWithPrecisionAndCountry>? releaseDates,
|
||||
List<String>? genres,
|
||||
List<TitleInLanguage>? titles}) {
|
||||
|
@ -68,6 +75,9 @@ class MovieData extends ChangeNotifier {
|
|||
if (bookmarked != null) {
|
||||
_bookmarked = bookmarked;
|
||||
}
|
||||
if (description != null) {
|
||||
_description = description;
|
||||
}
|
||||
if (releaseDates != null) {
|
||||
_releaseDates = releaseDates;
|
||||
}
|
||||
|
@ -99,6 +109,7 @@ class MovieData extends ChangeNotifier {
|
|||
"title": title,
|
||||
"releaseDate": _releaseDate.toJsonEncodable(),
|
||||
"bookmarked": _bookmarked,
|
||||
"description": _description,
|
||||
"releaseDates": releaseDatesByCountry,
|
||||
"genres": genres,
|
||||
"titles": titlesByCountry,
|
||||
|
@ -111,6 +122,7 @@ class MovieData extends ChangeNotifier {
|
|||
DateWithPrecisionAndCountry.fromJsonEncodable(json["releaseDate"]) {
|
||||
setDetails(
|
||||
bookmarked: json["bookmarked"] as bool,
|
||||
description: json["description"] as String?,
|
||||
genres: (json["genres"] as List<dynamic>?)
|
||||
?.map((genre) => genre as String)
|
||||
.toList(),
|
||||
|
|
|
@ -51,7 +51,8 @@ class MoviePage extends StatelessWidget {
|
|||
.toList() ??
|
||||
[],
|
||||
),
|
||||
const SizedBox(height: 20),
|
||||
const Heading("Description"),
|
||||
Text(movie.description ?? "No description"),
|
||||
const Heading("Titles"),
|
||||
Table(
|
||||
border: TableBorder.symmetric(
|
||||
|
|
Loading…
Reference in New Issue