282 lines
7.4 KiB
Factor
Executable File
282 lines
7.4 KiB
Factor
Executable File
! Copyright (C) 2007, 2008 Slava Pestov.
|
|
! See http://factorcode.org/license.txt for BSD license.
|
|
USING: kernel io io.styles io.files io.encodings.utf8
|
|
vocabs.loader vocabs sequences namespaces math.parser arrays
|
|
hashtables assocs memoize summary sorting splitting combinators
|
|
source-files debugger continuations compiler.errors init
|
|
checksums checksums.crc32 sets accessors ;
|
|
IN: tools.vocabs
|
|
|
|
: vocab-tests-file ( vocab -- path )
|
|
dup "-tests.factor" vocab-dir+ vocab-append-path dup
|
|
[ dup exists? [ drop f ] unless ] [ drop f ] if ;
|
|
|
|
: vocab-tests-dir ( vocab -- paths )
|
|
dup vocab-dir "tests" append-path vocab-append-path dup [
|
|
dup exists? [
|
|
dup directory keys
|
|
[ ".factor" tail? ] filter
|
|
[ append-path ] with map
|
|
] [ drop f ] if
|
|
] [ drop f ] if ;
|
|
|
|
: vocab-tests ( vocab -- tests )
|
|
[
|
|
[ vocab-tests-file [ , ] when* ]
|
|
[ vocab-tests-dir [ % ] when* ] bi
|
|
] { } make ;
|
|
|
|
: vocab-files ( vocab -- seq )
|
|
[
|
|
[ vocab-source-path [ , ] when* ]
|
|
[ vocab-docs-path [ , ] when* ]
|
|
[ vocab-tests % ] tri
|
|
] { } make ;
|
|
|
|
: vocab-heading. ( vocab -- )
|
|
nl
|
|
"==== " write
|
|
[ vocab-name ] [ vocab write-object ] bi ":" print
|
|
nl ;
|
|
|
|
: load-error. ( triple -- )
|
|
[ first vocab-heading. ] [ second print-error ] bi ;
|
|
|
|
: load-failures. ( failures -- )
|
|
[ load-error. nl ] each ;
|
|
|
|
SYMBOL: failures
|
|
|
|
: require-all ( vocabs -- failures )
|
|
[
|
|
V{ } clone blacklist set
|
|
V{ } clone failures set
|
|
[
|
|
[ require ]
|
|
[ swap vocab-name failures get set-at ]
|
|
recover
|
|
] each
|
|
failures get
|
|
] with-compiler-errors ;
|
|
|
|
: source-modified? ( path -- ? )
|
|
dup source-files get at [
|
|
dup path>>
|
|
dup exists? [
|
|
utf8 file-lines crc32 checksum-lines
|
|
swap checksum>> = not
|
|
] [
|
|
2drop f
|
|
] if
|
|
] [
|
|
exists?
|
|
] ?if ;
|
|
|
|
SYMBOL: changed-vocabs
|
|
|
|
[ f changed-vocabs set-global ] "tools.vocabs" add-init-hook
|
|
|
|
: changed-vocab ( vocab -- )
|
|
dup vocab changed-vocabs get and
|
|
[ dup changed-vocabs get set-at ] [ drop ] if ;
|
|
|
|
: unchanged-vocab ( vocab -- )
|
|
changed-vocabs get delete-at ;
|
|
|
|
: unchanged-vocabs ( vocabs -- )
|
|
[ unchanged-vocab ] each ;
|
|
|
|
: changed-vocab? ( vocab -- ? )
|
|
changed-vocabs get dup [ key? ] [ 2drop t ] if ;
|
|
|
|
: filter-changed ( vocabs -- vocabs' )
|
|
[ changed-vocab? ] filter ;
|
|
|
|
SYMBOL: modified-sources
|
|
SYMBOL: modified-docs
|
|
|
|
: (to-refresh) ( vocab variable loaded? path -- )
|
|
dup [
|
|
swap [
|
|
pick changed-vocab? [
|
|
source-modified? [ get push ] [ 2drop ] if
|
|
] [ 3drop ] if
|
|
] [ drop get push ] if
|
|
] [ 2drop 2drop ] if ;
|
|
|
|
: to-refresh ( prefix -- modified-sources modified-docs unchanged )
|
|
[
|
|
V{ } clone modified-sources set
|
|
V{ } clone modified-docs set
|
|
|
|
child-vocabs [
|
|
[
|
|
[
|
|
[ modified-sources ]
|
|
[ vocab-source-loaded? ]
|
|
[ vocab-source-path ]
|
|
tri (to-refresh)
|
|
] [
|
|
[ modified-docs ]
|
|
[ vocab-docs-loaded? ]
|
|
[ vocab-docs-path ]
|
|
tri (to-refresh)
|
|
] bi
|
|
] each
|
|
|
|
modified-sources get
|
|
modified-docs get
|
|
]
|
|
[ modified-docs get modified-sources get append diff ] bi
|
|
] with-scope ;
|
|
|
|
: do-refresh ( modified-sources modified-docs unchanged -- )
|
|
unchanged-vocabs
|
|
[
|
|
[ [ f swap set-vocab-source-loaded? ] each ]
|
|
[ [ f swap set-vocab-docs-loaded? ] each ] bi*
|
|
]
|
|
[
|
|
append prune
|
|
[ unchanged-vocabs ]
|
|
[ require-all load-failures. ] bi
|
|
] 2bi ;
|
|
|
|
: refresh ( prefix -- ) to-refresh do-refresh ;
|
|
|
|
: refresh-all ( -- ) "" refresh ;
|
|
|
|
MEMO: vocab-file-contents ( vocab name -- seq )
|
|
vocab-append-path dup
|
|
[ dup exists? [ utf8 file-lines ] [ drop f ] if ] when ;
|
|
|
|
: set-vocab-file-contents ( seq vocab name -- )
|
|
dupd vocab-append-path [
|
|
utf8 set-file-lines
|
|
\ vocab-file-contents reset-memoized
|
|
] [
|
|
"The " swap vocab-name
|
|
" vocabulary was not loaded from the file system"
|
|
3append throw
|
|
] ?if ;
|
|
|
|
: vocab-summary-path ( vocab -- string )
|
|
vocab-dir "summary.txt" append-path ;
|
|
|
|
: vocab-summary ( vocab -- summary )
|
|
dup dup vocab-summary-path vocab-file-contents
|
|
dup empty? [
|
|
drop vocab-name " vocabulary" append
|
|
] [
|
|
nip first
|
|
] if ;
|
|
|
|
M: vocab summary
|
|
[
|
|
dup vocab-summary %
|
|
" (" %
|
|
vocab-words assoc-size #
|
|
" words)" %
|
|
] "" make ;
|
|
|
|
M: vocab-link summary vocab-summary ;
|
|
|
|
: set-vocab-summary ( string vocab -- )
|
|
>r 1array r>
|
|
dup vocab-summary-path
|
|
set-vocab-file-contents ;
|
|
|
|
: vocab-tags-path ( vocab -- string )
|
|
vocab-dir "tags.txt" append-path ;
|
|
|
|
: vocab-tags ( vocab -- tags )
|
|
dup vocab-tags-path vocab-file-contents ;
|
|
|
|
: set-vocab-tags ( tags vocab -- )
|
|
dup vocab-tags-path set-vocab-file-contents ;
|
|
|
|
: add-vocab-tags ( tags vocab -- )
|
|
[ vocab-tags append prune ] keep set-vocab-tags ;
|
|
|
|
: vocab-authors-path ( vocab -- string )
|
|
vocab-dir "authors.txt" append-path ;
|
|
|
|
: vocab-authors ( vocab -- authors )
|
|
dup vocab-authors-path vocab-file-contents ;
|
|
|
|
: set-vocab-authors ( authors vocab -- )
|
|
dup vocab-authors-path set-vocab-file-contents ;
|
|
|
|
: subdirs ( dir -- dirs )
|
|
directory [ second ] filter keys natural-sort ;
|
|
|
|
: (all-child-vocabs) ( root name -- vocabs )
|
|
[ vocab-dir append-path subdirs ] keep
|
|
dup empty? [
|
|
drop
|
|
] [
|
|
swap [ "." swap 3append ] with map
|
|
] if ;
|
|
|
|
: vocabs-in-dir ( root name -- )
|
|
dupd (all-child-vocabs) [
|
|
2dup vocab-dir? [ dup >vocab-link , ] when
|
|
vocabs-in-dir
|
|
] with each ;
|
|
|
|
: all-vocabs ( -- assoc )
|
|
vocab-roots get [
|
|
dup [ "" vocabs-in-dir ] { } make
|
|
] { } map>assoc ;
|
|
|
|
MEMO: all-vocabs-seq ( -- seq )
|
|
all-vocabs values concat ;
|
|
|
|
: unportable? ( name -- ? )
|
|
vocab-tags "unportable" swap member? ;
|
|
|
|
: filter-unportable ( seq -- seq' )
|
|
[ vocab-name unportable? not ] filter ;
|
|
|
|
: try-everything ( -- failures )
|
|
all-vocabs-seq
|
|
filter-unportable
|
|
require-all ;
|
|
|
|
: load-everything ( -- )
|
|
try-everything load-failures. ;
|
|
|
|
: unrooted-child-vocabs ( prefix -- seq )
|
|
dup empty? [ CHAR: . suffix ] unless
|
|
vocabs
|
|
[ find-vocab-root not ] filter
|
|
[
|
|
vocab-name swap ?head CHAR: . rot member? not and
|
|
] with filter
|
|
[ vocab ] map ;
|
|
|
|
: all-child-vocabs ( prefix -- assoc )
|
|
vocab-roots get [
|
|
dup pick (all-child-vocabs) [ >vocab-link ] map
|
|
] { } map>assoc
|
|
swap unrooted-child-vocabs f swap 2array suffix ;
|
|
|
|
: all-child-vocabs-seq ( prefix -- assoc )
|
|
vocab-roots get swap [
|
|
dupd (all-child-vocabs)
|
|
[ vocab-dir? ] with filter
|
|
] curry map concat ;
|
|
|
|
MEMO: all-tags ( -- seq )
|
|
all-vocabs-seq [ vocab-tags ] gather natural-sort ;
|
|
|
|
MEMO: all-authors ( -- seq )
|
|
all-vocabs-seq [ vocab-authors ] gather natural-sort ;
|
|
|
|
: reset-cache ( -- )
|
|
root-cache get-global clear-assoc
|
|
\ vocab-file-contents reset-memoized
|
|
\ all-vocabs-seq reset-memoized
|
|
\ all-authors reset-memoized
|
|
\ all-tags reset-memoized ;
|