use v6.e.PREVIEW; use JSON::Class:auth; #| Shared post meta-data unit role Post is json; #| The location of the source file for the post has IO::Path:D $.source is required is json( :to-json(*.Str), :from-json(*.IO) ); #| The time to display for the creation of the post has DateTime:D $.posted-at is rw is required is json( :to-json(*.Str), :from-json(*.DateTime) ); #| An optional list of edit times for the post has DateTime:D @.edited-at is rw is json( :to-json( value => { $^value.Str } ), :from-json( value => { $^value.DateTime } ) ) = []; #| An optional list of extra slugs to use for this post has Str:D @.slugs is json = []; #| An optional list of tags for this post has Str:D @.tags is rw is json = []; #| Should the post be hidden from the main list has Bool:D $.hidden is json is rw = False; #| An optional link to the source code for the post has Str $.source-code is rw is json; #| Get the title for this post, intended to be extracted from whatever #| document produced it method title(--> Str:D) {...} #| The time the post was last updated at method updated(--> DateTime:D) { if @!edited-at { @!edited-at.max } else { $!posted-at } } #| Get the list of slugs for this post, including ones auto generated from #| the title, as well as any additional slugs method all-slugs(--> Array[Str:D]) { my $title-words = self.title.lc.trim.words; my $long-title-slug = $title-words.join('-'); my $six-word-slug = self.title.lc.words.head(6).join('-'); my Str:D @slugs = @!slugs.clone; @slugs.push($long-title-slug); @slugs.push($six-word-slug); @slugs.=unique; @slugs } #| Render this post to an html body method render-html(--> Str:D) {...} #| Get the description for this post, returning nil if there is none method description(--> Str) { Nil } #| Estimated readtimes at 140/180/220 wpm method readtimes() { my $word-count = $!source.slurp.words.elems; ($word-count / 140, $word-count / 180, $word-count / 220).map(*.ceiling) }