contacts = null; } /** @var string */ protected $table = 'notes'; /** @var array */ protected $fillable = [ 'note', 'in_reply_to', 'client_id', ]; /** @var array */ protected $hidden = ['searchable']; public function tags(): BelongsToMany { return $this->belongsToMany(Tag::class); } public function client(): BelongsTo { return $this->belongsTo(MicropubClient::class, 'client_id', 'client_url'); } public function webmentions(): MorphMany { return $this->morphMany(WebMention::class, 'commentable'); } public function place(): BelongsTo { return $this->belongsTo(Place::class); } public function media(): HasMany { return $this->hasMany(Media::class); } /** * @return array */ public function toSearchableArray(): array { return [ 'note' => $this->note, ]; } public function setNoteAttribute(?string $value): void { if ($value !== null) { $normalized = normalizer_normalize($value, Normalizer::FORM_C); if ($normalized === '') { // we don’t want to save empty strings to the db $normalized = null; } $this->attributes['note'] = $normalized; } } /** * Pre-process notes for web-view. */ public function getNoteAttribute(?string $value): ?string { if ($value === null && $this->place !== null) { $value = '📍: ' . $this->place->name . ''; } // if $value is still null, just return null if ($value === null) { return null; } $hashtags = $this->autoLinkHashtag($value); return $this->convertMarkdown($hashtags); } /** * Provide the content_html for JSON feed. * * In particular, we want to include media links such as images. */ public function getContentAttribute(): string { $note = $this->getRawOriginal('note'); foreach ($this->media as $media) { if ($media->type === 'image') { $note .= PHP_EOL . ''; } if ($media->type === 'audio') { $note .= PHP_EOL . '