UNPKG

wikibase-edit

Version:

Edit Wikibase from NodeJS

107 lines (90 loc) 3.55 kB
import { isGuid, getEntityIdFromGuid, type Guid, type PropertyId, type Rank, type Claim, type SnakBase } from 'wikibase-sdk' import { newError } from '../error.js' import { getEntityClaims } from '../get_entity.js' import { findSnak } from './find_snak.js' import { findClaimByGuid, isGuidClaim, simplifyClaimForEdit } from './helpers.js' import { hasSpecialSnaktype } from './special_snaktype.js' import type { EditEntitySimplifiedModeParams } from '../entity/edit.js' import type { WikibaseEditAPI } from '../index.js' import type { BaseRevId } from '../types/common.js' import type { SerializedConfig } from '../types/config.js' import type { RawEditableEntity } from '../types/edit_entity.js' import type { EditableMonolingualTextSnakValue, EditableSnakValue } from '../types/snaks.js' export interface UpdateClaimParams { id?: RawEditableEntity['id'] guid?: Guid<RawEditableEntity['id']> property?: PropertyId oldValue?: EditableSnakValue newValue?: EditableSnakValue rank?: Rank summary?: string baserevid?: BaseRevId } export async function updateClaim (params: UpdateClaimParams, config: SerializedConfig, API: WikibaseEditAPI) { let { id, guid, property } = params const { oldValue, newValue, rank } = params const { statementsKey } = config if (!(rank != null || newValue != null)) { throw newError('expected a rank or a newValue', 400, params) } if (isGuid(guid)) { id = getEntityIdFromGuid(guid) as RawEditableEntity['id'] } else { const values = { oldValue, newValue } if (oldValue === newValue) { throw newError("old and new claim values can't be the same", 400, values) } if (typeof oldValue !== typeof newValue) { throw newError('old and new claim should have the same type', 400, values) } } const claims = await getEntityClaims(id, config) let claim if (guid) { claim = findClaimByGuid(claims, guid) property = claim?.mainsnak.property } else { claim = findSnak(property, claims[property] as Claim[], oldValue) } if (!claim) { throw newError('claim not found', 400, params) } const simplifiedClaim = simplifyClaimForEdit(claim) guid = claim.id if (rank) simplifiedClaim.rank = rank if (newValue != null) { if (hasSpecialSnaktype(newValue)) { simplifiedClaim.snaktype = newValue.snaktype delete simplifiedClaim.value } else { simplifiedClaim.value = formatUpdatedSnakValue(newValue, claim.mainsnak) } } const data: EditEntitySimplifiedModeParams = { id, [statementsKey]: { [property]: simplifiedClaim, }, // Using wbeditentity, as the endpoint is more complete, so we need to recover the summary summary: params.summary || config.summary || `update ${property} claim`, baserevid: params.baserevid || config.baserevid, } const { entity, success } = await API.entity.edit(data, config) const updatedClaim = entity[statementsKey][property].find(isGuidClaim(guid)) // Mimick claim actions responses return { claim: updatedClaim, success } } export function formatUpdatedSnakValue (newValue: EditableSnakValue, updatedSnak: SnakBase) { if (updatedSnak.snaktype !== 'value') return newValue const { type } = updatedSnak.datavalue if (type === 'monolingualtext' && typeof newValue === 'string') { const { language } = updatedSnak.datavalue.value return { text: newValue, language } as EditableMonolingualTextSnakValue } else { return newValue } } export interface UpdateClaimResponse { claim: Claim success: 1 }