mirror of
https://github.com/flynx/pWiki.git
synced 2025-11-02 12:00:10 +00:00
reworking store API to be sync/async...
Signed-off-by: Alex A. Naanou <alex.nanou@gmail.com>
This commit is contained in:
parent
8acb914237
commit
d4a1e3f055
@ -541,6 +541,40 @@ object.Constructor('BasePage', {
|
|||||||
}) },
|
}) },
|
||||||
|
|
||||||
// XXX should this be an iterator???
|
// XXX should this be an iterator???
|
||||||
|
// XXX EXPERIMENTAL...
|
||||||
|
// to be sync this needs:
|
||||||
|
// .energetic
|
||||||
|
// .store.isEnergetic(..)
|
||||||
|
// .resolve(..) -> .store.resolve(..)
|
||||||
|
each: function(path){
|
||||||
|
var that = this
|
||||||
|
// NOTE: we are trying to avoid resolving non-pattern paths unless
|
||||||
|
// we really have to...
|
||||||
|
path = path ?
|
||||||
|
pwpath.relative(this.path, path)
|
||||||
|
: this.location
|
||||||
|
var paths = path.includes('*') ?
|
||||||
|
Promise.awaitOrRun(
|
||||||
|
this.energetic,
|
||||||
|
this.store.isEnergetic(path),
|
||||||
|
function(a, b){
|
||||||
|
return !(a || b) ?
|
||||||
|
that.resolve(path)
|
||||||
|
: path })
|
||||||
|
: path
|
||||||
|
paths = Promise.awaitOrRun(
|
||||||
|
paths,
|
||||||
|
function(paths){
|
||||||
|
return (paths instanceof Array
|
||||||
|
|| paths instanceof Promise) ?
|
||||||
|
paths
|
||||||
|
: [paths] })
|
||||||
|
return Promise.iter(
|
||||||
|
paths,
|
||||||
|
function(path){
|
||||||
|
return that.get('/'+ path) })
|
||||||
|
.sync() },
|
||||||
|
/*/ // XXX ASYNC...
|
||||||
each: async function*(path){
|
each: async function*(path){
|
||||||
// NOTE: we are trying to avoid resolving non-pattern paths unless
|
// NOTE: we are trying to avoid resolving non-pattern paths unless
|
||||||
// we really have to...
|
// we really have to...
|
||||||
@ -561,14 +595,15 @@ object.Constructor('BasePage', {
|
|||||||
: [paths]
|
: [paths]
|
||||||
for(var path of paths){
|
for(var path of paths){
|
||||||
yield this.get('/'+ path) } },
|
yield this.get('/'+ path) } },
|
||||||
|
//*/
|
||||||
[Symbol.asyncIterator]: async function*(){
|
[Symbol.asyncIterator]: async function*(){
|
||||||
yield* this.each() },
|
yield* this.each() },
|
||||||
|
|
||||||
map: async function(func){
|
map: function(func){
|
||||||
return this.each().map(func) },
|
return this.each().map(func) },
|
||||||
filter: async function(func){
|
filter: function(func){
|
||||||
return this.each().filter(func) },
|
return this.each().filter(func) },
|
||||||
reduce: async function(func, dfl){
|
reduce: function(func, dfl){
|
||||||
return this.each().reduce(func, dfl) },
|
return this.each().reduce(func, dfl) },
|
||||||
|
|
||||||
// sorting...
|
// sorting...
|
||||||
@ -1842,6 +1877,52 @@ object.Constructor('Page', BasePage, {
|
|||||||
// actions...
|
// actions...
|
||||||
//
|
//
|
||||||
// XXX revise name...
|
// XXX revise name...
|
||||||
|
/*/ XXX EXPERIMENTAL
|
||||||
|
asPages: function(path='.:$ARGS', strict=false){
|
||||||
|
// options...
|
||||||
|
var args = [...arguments]
|
||||||
|
var opts = typeof(args.at(-1)) == 'object' ?
|
||||||
|
args.pop()
|
||||||
|
: {}
|
||||||
|
var {path, strict} = {
|
||||||
|
...opts,
|
||||||
|
path: typeof(args[0]) == 'string' ?
|
||||||
|
args.shift()
|
||||||
|
: '.:$ARGS',
|
||||||
|
strict: args.shift()
|
||||||
|
?? false,
|
||||||
|
}
|
||||||
|
|
||||||
|
var page = this.get(path, strict)
|
||||||
|
// each...
|
||||||
|
if(page.isPattern){
|
||||||
|
return page.each()
|
||||||
|
// handle lists in pages (actions, ... etc.)...
|
||||||
|
} else {
|
||||||
|
return Promise.awaitOrRun(
|
||||||
|
page.data,
|
||||||
|
function(data){
|
||||||
|
data =
|
||||||
|
data instanceof types.Generator ?
|
||||||
|
// XXX
|
||||||
|
//await data()
|
||||||
|
data()
|
||||||
|
: typeof(data) == 'function' ?
|
||||||
|
data
|
||||||
|
: data && 'text' in data ?
|
||||||
|
data.text
|
||||||
|
: null
|
||||||
|
if(data instanceof Array
|
||||||
|
|| data instanceof types.Generator){
|
||||||
|
return data
|
||||||
|
.map(function(p){
|
||||||
|
return page.virtual({text: p}) }) }
|
||||||
|
// do not iterate pages/actions that are undefined...
|
||||||
|
if(data == null){
|
||||||
|
return }
|
||||||
|
|
||||||
|
return page }) } },
|
||||||
|
/*/ // XXX ASYNC...
|
||||||
asPages: async function*(path='.:$ARGS', strict=false){
|
asPages: async function*(path='.:$ARGS', strict=false){
|
||||||
// options...
|
// options...
|
||||||
var args = [...arguments]
|
var args = [...arguments]
|
||||||
@ -1883,6 +1964,7 @@ object.Constructor('Page', BasePage, {
|
|||||||
return }
|
return }
|
||||||
|
|
||||||
yield page } },
|
yield page } },
|
||||||
|
//*/
|
||||||
|
|
||||||
// expanded page text...
|
// expanded page text...
|
||||||
//
|
//
|
||||||
|
|||||||
@ -886,6 +886,27 @@ module.BaseStore = {
|
|||||||
//
|
//
|
||||||
// NOTE: handlers are run in order of definition.
|
// NOTE: handlers are run in order of definition.
|
||||||
//
|
//
|
||||||
|
// XXX EXPERIMENTAL
|
||||||
|
tags: function(tags){
|
||||||
|
var that = this
|
||||||
|
tags = typeof(tags) == 'string' ?
|
||||||
|
this.parseTags(tags)
|
||||||
|
: false
|
||||||
|
return Promise.awaitOrRun(
|
||||||
|
tags
|
||||||
|
&& this.tags,
|
||||||
|
function(tags){
|
||||||
|
return tags
|
||||||
|
&& function(path){
|
||||||
|
// tags -> skip untagged pages...
|
||||||
|
var t = this.tags.paths[path]
|
||||||
|
if(!t){
|
||||||
|
return false }
|
||||||
|
for(var tag of tags){
|
||||||
|
if(!t || !t.has(tag)){
|
||||||
|
return false } }
|
||||||
|
return true } }) },
|
||||||
|
/*/ // XXX ASYNC...
|
||||||
tags: async function(tags){
|
tags: async function(tags){
|
||||||
tags = typeof(tags) == 'string' ?
|
tags = typeof(tags) == 'string' ?
|
||||||
this.parseTags(tags)
|
this.parseTags(tags)
|
||||||
@ -901,6 +922,7 @@ module.BaseStore = {
|
|||||||
if(!t || !t.has(tag)){
|
if(!t || !t.has(tag)){
|
||||||
return false } }
|
return false } }
|
||||||
return true } },
|
return true } },
|
||||||
|
//*/
|
||||||
search: async function(search){
|
search: async function(search){
|
||||||
search = search
|
search = search
|
||||||
&& new Set(await this.search(search))
|
&& new Set(await this.search(search))
|
||||||
@ -926,6 +948,27 @@ module.BaseStore = {
|
|||||||
count--
|
count--
|
||||||
return !!(count >= 0) } },
|
return !!(count >= 0) } },
|
||||||
},
|
},
|
||||||
|
// XXX EXPERIMENTAL...
|
||||||
|
__match_args: function(args){
|
||||||
|
var that = this
|
||||||
|
var predicates = []
|
||||||
|
for(var [key, gen] of Object.entries(this.__match_args__ ?? {})){
|
||||||
|
var p = gen.call(this, args[key], args)
|
||||||
|
p && predicates.push(p) }
|
||||||
|
return Promise.awaitOrRun(
|
||||||
|
...predicates,
|
||||||
|
function(...predicates){
|
||||||
|
predicates = predicates
|
||||||
|
.filter(function(p){ return p })
|
||||||
|
return predicates.length > 0 ?
|
||||||
|
function(path){
|
||||||
|
for(var p of predicates){
|
||||||
|
if(!p.call(that, path)){
|
||||||
|
return false } }
|
||||||
|
return true }
|
||||||
|
: undefined },
|
||||||
|
null) },
|
||||||
|
/*/ // XXX ASYNC...
|
||||||
__match_args: async function(args){
|
__match_args: async function(args){
|
||||||
var that = this
|
var that = this
|
||||||
var predicates = []
|
var predicates = []
|
||||||
@ -939,7 +982,12 @@ module.BaseStore = {
|
|||||||
return false } }
|
return false } }
|
||||||
return true }
|
return true }
|
||||||
: undefined },
|
: undefined },
|
||||||
match: async function(path, strict=false){
|
//*/
|
||||||
|
// XXX EXPERIMENTAL...
|
||||||
|
// to be sync this needs:
|
||||||
|
// .__match_args(..) -- DONE
|
||||||
|
// .metadata(..)
|
||||||
|
match: function(path, strict=false){
|
||||||
var that = this
|
var that = this
|
||||||
// pattern match * / **
|
// pattern match * / **
|
||||||
if(path.includes('*')
|
if(path.includes('*')
|
||||||
@ -954,10 +1002,14 @@ module.BaseStore = {
|
|||||||
?? !(args.sortnewfirst
|
?? !(args.sortnewfirst
|
||||||
// default is sortnewlast...
|
// default is sortnewlast...
|
||||||
?? false)
|
?? false)
|
||||||
var test = await this.__match_args(args)
|
|
||||||
|
var test = this.__match_args(args)
|
||||||
args = pwpath.joinArgs('', args)
|
args = pwpath.joinArgs('', args)
|
||||||
|
|
||||||
var order = (await this.metadata(path) ?? {}).order || []
|
var order = Promise.awaitOrRun(
|
||||||
|
this.metadata(path),
|
||||||
|
function(metadata){
|
||||||
|
return (metadata ?? {}).order || [] })
|
||||||
|
|
||||||
// NOTE: we are matching full paths only here so leading and
|
// NOTE: we are matching full paths only here so leading and
|
||||||
// trainling '/' are optional...
|
// trainling '/' are optional...
|
||||||
@ -970,7 +1022,13 @@ module.BaseStore = {
|
|||||||
// dir for hidden tests...
|
// dir for hidden tests...
|
||||||
.replace(/(^|\\\/+)(\\\.|)([^\/]*)\\\*/g, '$1$2($3[^\\/]*)')
|
.replace(/(^|\\\/+)(\\\.|)([^\/]*)\\\*/g, '$1$2($3[^\\/]*)')
|
||||||
+'(?=[\\/]|$)', 'g')
|
+'(?=[\\/]|$)', 'g')
|
||||||
return [...(await this.paths)
|
// XXX ASYNC...
|
||||||
|
return Promise.awaitOrRun(
|
||||||
|
this.paths,
|
||||||
|
test,
|
||||||
|
order,
|
||||||
|
function(paths, test, order){
|
||||||
|
return [...paths
|
||||||
// NOTE: we are not using .filter(..) here as wee
|
// NOTE: we are not using .filter(..) here as wee
|
||||||
// need to keep parts of the path only and not
|
// need to keep parts of the path only and not
|
||||||
// return the whole thing...
|
// return the whole thing...
|
||||||
@ -1013,15 +1071,100 @@ module.BaseStore = {
|
|||||||
return (sort && sort !== true) ?
|
return (sort && sort !== true) ?
|
||||||
that
|
that
|
||||||
.sort(this, ...sort.split(/\s*[,\s]+/g))
|
.sort(this, ...sort.split(/\s*[,\s]+/g))
|
||||||
:this
|
: this
|
||||||
.sortAs(order,
|
.sortAs(order,
|
||||||
newlast ?
|
newlast ?
|
||||||
'head'
|
'head'
|
||||||
: 'tail') })
|
: 'tail') })
|
||||||
.map(function(p){
|
.map(function(p){
|
||||||
return p+args })}
|
return p+args }) }) }
|
||||||
// direct search...
|
// direct search...
|
||||||
return this.find(path, strict) },
|
return this.find(path, strict) },
|
||||||
|
// // XXX ASYNC...
|
||||||
|
// match: async function(path, strict=false){
|
||||||
|
// var that = this
|
||||||
|
// // pattern match * / **
|
||||||
|
// if(path.includes('*')
|
||||||
|
// || path.includes('**')){
|
||||||
|
// var {path, args} = pwpath.splitArgs(path)
|
||||||
|
// path = pwpath.sanitize(path)
|
||||||
|
//
|
||||||
|
// var all = args.all
|
||||||
|
// var sort = args.sort
|
||||||
|
// var newlast =
|
||||||
|
// args.sortnewlast
|
||||||
|
// ?? !(args.sortnewfirst
|
||||||
|
// // default is sortnewlast...
|
||||||
|
// ?? false)
|
||||||
|
// var test = await this.__match_args(args)
|
||||||
|
// args = pwpath.joinArgs('', args)
|
||||||
|
//
|
||||||
|
// var order = (await this.metadata(path) ?? {}).order || []
|
||||||
|
//
|
||||||
|
// // NOTE: we are matching full paths only here so leading and
|
||||||
|
// // trainling '/' are optional...
|
||||||
|
// var pattern = new RegExp(`^\\/?`
|
||||||
|
// +RegExp.quoteRegExp(path)
|
||||||
|
// // pattern: **
|
||||||
|
// .replace(/\\\*\\\*/g, '(.*)')
|
||||||
|
// // pattern: *
|
||||||
|
// // NOTE: we are prepping the leading '.' of a pattern
|
||||||
|
// // dir for hidden tests...
|
||||||
|
// .replace(/(^|\\\/+)(\\\.|)([^\/]*)\\\*/g, '$1$2($3[^\\/]*)')
|
||||||
|
// +'(?=[\\/]|$)', 'g')
|
||||||
|
// return [...(await this.paths)
|
||||||
|
// // NOTE: we are not using .filter(..) here as wee
|
||||||
|
// // need to keep parts of the path only and not
|
||||||
|
// // return the whole thing...
|
||||||
|
// .reduce(function(res, p){
|
||||||
|
// // skip metadata paths...
|
||||||
|
// if(p.includes('*')){
|
||||||
|
// return res }
|
||||||
|
// // check path: stage 1
|
||||||
|
// var m = [...p.matchAll(pattern)]
|
||||||
|
// var visible = m.length > 0
|
||||||
|
// && (!all ?
|
||||||
|
// // test if we need to hide things....
|
||||||
|
// m.reduce(function(res, m){
|
||||||
|
// return res === false ?
|
||||||
|
// res
|
||||||
|
// : !/(^\.|[\\\/]\.)/.test(m[1])
|
||||||
|
// }, true)
|
||||||
|
// : true)
|
||||||
|
// // args...
|
||||||
|
// // NOTE: this needs to be between path checking
|
||||||
|
// // stages as we need to skip paths depending
|
||||||
|
// // on the all argument...
|
||||||
|
// if(visible
|
||||||
|
// && test
|
||||||
|
// && !test(p)){
|
||||||
|
// return res }
|
||||||
|
// // check path: stage 2
|
||||||
|
// visible
|
||||||
|
// && (m = m[0])
|
||||||
|
// && (!strict
|
||||||
|
// || m[0] == p)
|
||||||
|
// && res.add(
|
||||||
|
// // normalize the path elements...
|
||||||
|
// m[0][0] == '/' ?
|
||||||
|
// m[0].slice(1)
|
||||||
|
// : m[0])
|
||||||
|
// return res }, new Set())]
|
||||||
|
// // handle live sort...
|
||||||
|
// .run(function(){
|
||||||
|
// return (sort && sort !== true) ?
|
||||||
|
// that
|
||||||
|
// .sort(this, ...sort.split(/\s*[,\s]+/g))
|
||||||
|
// :this
|
||||||
|
// .sortAs(order,
|
||||||
|
// newlast ?
|
||||||
|
// 'head'
|
||||||
|
// : 'tail') })
|
||||||
|
// .map(function(p){
|
||||||
|
// return p+args })}
|
||||||
|
// // direct search...
|
||||||
|
// return this.find(path, strict) },
|
||||||
|
//*/
|
||||||
//
|
//
|
||||||
// .resolve(<path>)
|
// .resolve(<path>)
|
||||||
// -> <path>
|
// -> <path>
|
||||||
@ -1039,6 +1182,32 @@ module.BaseStore = {
|
|||||||
// -> ['System/tree', 'Dir/tree', ...]
|
// -> ['System/tree', 'Dir/tree', ...]
|
||||||
//
|
//
|
||||||
// XXX should this be used by .get(..) instead of .match(..)???
|
// XXX should this be used by .get(..) instead of .match(..)???
|
||||||
|
// XXX EXPERIMENTAL
|
||||||
|
// to be sync requires:
|
||||||
|
// .match(..)
|
||||||
|
resolve: function(path, strict){
|
||||||
|
// pattern match * / **
|
||||||
|
if(path.includes('*')
|
||||||
|
|| path.includes('**')){
|
||||||
|
var p = pwpath.splitArgs(path)
|
||||||
|
var args = pwpath.joinArgs('', p.args)
|
||||||
|
p = pwpath.split(p.path)
|
||||||
|
var tail = []
|
||||||
|
while(!p.at(-1).includes('*')){
|
||||||
|
tail.unshift(p.pop()) }
|
||||||
|
tail = tail.join('/')
|
||||||
|
if(tail.length > 0){
|
||||||
|
return Promise
|
||||||
|
.iter(this.match(
|
||||||
|
p.join('/') + args,
|
||||||
|
strict))
|
||||||
|
.map(function(p){
|
||||||
|
var {path, args} = pwpath.splitArgs(p)
|
||||||
|
return pwpath.joinArgs(pwpath.join(path, tail), args) })
|
||||||
|
.sync() } }
|
||||||
|
// direct...
|
||||||
|
return this.match(path, strict) },
|
||||||
|
/*/ // XXX ASYNC...
|
||||||
resolve: async function(path, strict){
|
resolve: async function(path, strict){
|
||||||
// pattern match * / **
|
// pattern match * / **
|
||||||
if(path.includes('*')
|
if(path.includes('*')
|
||||||
@ -1059,6 +1228,7 @@ module.BaseStore = {
|
|||||||
return pwpath.joinArgs(pwpath.join(path, tail), args) }) } }
|
return pwpath.joinArgs(pwpath.join(path, tail), args) }) } }
|
||||||
// direct...
|
// direct...
|
||||||
return this.match(path, strict) },
|
return this.match(path, strict) },
|
||||||
|
//*/
|
||||||
//
|
//
|
||||||
// Resolve page
|
// Resolve page
|
||||||
// .get(<path>)
|
// .get(<path>)
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user