Quantcast

Foswiki::META and 'many' syntax key

classic Classic list List threaded Threaded
4 messages Options
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Foswiki::META and 'many' syntax key

Belman Vadim
Good day,

While playing around with META it came over me that %syntax key ‘many’ of registerMETA() method is in fact respected by queries only. From Foswiki::Meta documentation I got an impression that the only difference of put and putKeyed methods is that the former one does respect ‘many’ by appending new attributes hash to the list of existing ones. That seems to be very illogical especially if we take into account that they both rely on the ‘name’ key of META attributes hash and yet this behavior isn’t even documented! The only notion of special meaning of the ‘name’ key found in description of get() functionality.

In my vision if keying of meta is the must then it’d be much better to allow defining the index key alongside with the `many’. Might look like:

registerMETA(…, many => 1, index => ‘id’ );

If I miss a point here and custom index field is a bad idea then it’d be a great idea to make documentation a little bit more informative.

PS. Method find() which finds nothing it’s… Shouldn't it be named ‘values()’ or something of the kind?

Belman Vadim





------------------------------------------------------------------------------
_______________________________________________
Foswiki-discuss mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/foswiki-discuss
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Foswiki::META and 'many' syntax key

Crawford Currie
Hi,

On 06/10/15 22:44, Belman Vadim wrote:
> While playing around with META it came over me that %syntax key ‘many’ of registerMETA() method is in fact respected by queries only. From Foswiki::Meta documentation I got an impression that the only difference of put and putKeyed methods is that the former one does respect ‘many’ by appending new attributes hash to the list of existing ones. That seems to be very illogical especially if we take into account that they both rely on the ‘name’ key of META attributes hash and yet this behavior isn’t even documented! The only notion of special meaning of the ‘name’ key found in description of get() functionality.
The API of Meta has a long and complex history. The basic API (put,
putKeyed, get, find) was created very early on (I don't know when, it
predates the earliest use of version control, long before I became
involved). They are still there because we have been forced to maintain
compatibility with old code that used the API. I introduced {many}
specifically to support query engines, to make it possible to know which
of get or find to use with a given meta type. I didn't redesign the API
at that time because of the volume of code already using the existing
API pushed it way beyond the scope of what I was doing. Perhaps I should
have done.
> In my vision if keying of meta is the must then it’d be much better to allow defining the index key alongside with the `many’. Might look like:
>
> registerMETA(…, many => 1, index => ‘id’ );
>
> If I miss a point here and custom index field is a bad idea then it’d be a great idea to make documentation a little bit more informative.
>
> PS. Method find() which finds nothing it’s… Shouldn't it be named ‘values()’ or something of the kind?
Frankly if I was going to redesign the API I wouldn't attempt to tweak
what is already there. I'd design a completely new Meta object from the
ground up. It *may* be possible to support the existing API in that case
using ties, but frankly I doubt it; abuses of the API are so widespread
that it would be almost impossible to track them all down.

C.




------------------------------------------------------------------------------
Full-scale, agent-less Infrastructure Monitoring from a single dashboard
Integrate with 40+ ManageEngine ITSM Solutions for complete visibility
Physical-Virtual-Cloud Infrastructure monitoring from one console
Real user monitoring with APM Insights and performance trend reports
Learn More http://pubads.g.doubleclick.net/gampad/clk?id=247754911&iu=/4140
_______________________________________________
Foswiki-discuss mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/foswiki-discuss
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Foswiki::META and 'many' syntax key

Julian Levens
Hi
 
I've also had fun playing with META, and as you say it's quite illogical, but as Crawford points out that's legacy for you.
 
Way below is the output of a script I wrote to check out some of the oddities.
 
However, I have thought for a while that we could clean up a little.
 
Basically if 'name' is one of the keys then treat this as putKeyed otherwise put (I'll discuss exceptions later).
 
It's worth noting that the code that rebuilds META from the topic text has the following logic.
 
       if ( defined( $keys->{name} ) ) {
 
            # save it keyed if it has a name
            $meta->putKeyed( $type, $keys );
        }
        else {
            $meta->put( $type, $keys );
        }
 
That is, that when the topic is read back in, then it will be normalised like this anyway.
 
This also simplifies the docs to a programmer - always use putKeyed (amended to do put semantics when no 'name' key). 
 
I have recently scanned topics and found the following types of error:
 
%META:TOPICPARENT{name="WebHome"}%
%META:TOPICPARENT{name="AnotherHome"}%
 
%META:FORM{name="CakeForm"}%
%META:FORM{name="BakingForm"}%
 
That is repetition of certain META:TYPEs that despite the 'name' key should actually be treated as un-named. However, a programmer has been confused (not that I blame them) and used putKeyed rather than put. The difficulty is that you have to know these exceptions.
 
For consistency these META:TYPES should have been:
 
%META:PARENT{topic="WebHome"}%
%META:FORM{topic="CakeForm"}%
 
i.e. no 'name' key and therefore not indexed. However, that's legacy
 
I would have preferred registerMETA to assume {many} if a 'name' field is {allowed} or {required} unless marked as say {singleton}. This information is already in the standard registerMETA structure.
 
Ultimately, I suppose I'm suggesting that put or putKeyed become the standard method call with the other deprecated. The remaining method would need to intelligently 'putKeyed' or 'put' based on the presence of the 'name' key unless that META:TYPE is marked as a singleton. Also, new singleton types with a 'name' key should not be created in new code.
 
I'm not sure whether keys other than 'name' for {many} key types are required. It may indeed be better to standardise on 'name', but I'm still open there. I'd even wonder about registerMETA(..., many=>'name'); registerMETA(..., many=>"" ) (i.e. no key is hmm keyed, ergo a singleton type) or registerMETA(..., many='id'). There is much less legacy here and we could make possibly make changes.
 
Others may of course have objections, after all this is a discussion forum :)
 
Thanks
 
Julian Levens
 
# Script output with explanatory notes:-
 
# put( 'FRED', { fruit => 'Banana', state => 'raw' } )
# Simple put with no 'name' key for META:FRED
# Note creation of _indices 'FRED' entry albeit no values (it was not putkeyed)
$meta = {
  'FRED' => [
    {
      'fruit' => 'Banana',
      'state' => 'raw'
    }
  ],
  '_indices' => {
    'FRED' => {}
  }
};
 
# put( 'BILL', { fruit => 'cherry', state => 'Jam' } )
# Simple put with no 'name' key for META:BILL a different TYPE than above
# Note creation of _indices 'BILL' entry albeit no values (it was not putkeyed)
$meta = {
  'BILL' => [
    {
      'fruit' => 'cherry',
      'state' => 'Jam'
    }
  ],
  'FRED' => [
    {
      'fruit' => 'Banana',
      'state' => 'raw'
    }
  ],
  '_indices' => {
    'BILL' => {},
    'FRED' => {}
  }
};
 
put( 'FRED', { fruit => 'Pineapple', state => 'coulis' } )
# Repeat put with no 'name' key for META:FRED
# Note 'FRED' is overwritten (it was not putkeyed)
$meta = {
  'BILL' => [
    {
      'fruit' => 'cherry',
      'state' => 'Jam'
    }
  ],
  'FRED' => [
    {
      'fruit' => 'Pineapple',
      'state' => 'coulis'
    }
  ],
  '_indices' => {
    'BILL' => {},
    'FRED' => {}
  }
};
 
$meta = {}; # Reset ready for tests using putKeyed
 
put( 'TYPE', { name => 'John' } )
# put with a 'name' key
# no other keys given as that adds nothing to the following illustrations
# therefore index 0 'John' created
$meta = {
  'TYPE' => [
    {
      'name' => 'John'
    }
  ],
  '_indices' => {
    'TYPE' => {
      'John' => 0
    }
  }
};
 
put( 'TYPE', { name => 'Mary' } )
# put with a different 'name' key than above
# therefore index 0 'John' overwritten with 'Mary' it was not putKeyed
$meta = {
  'TYPE' => [
    {
      'name' => 'Mary'
    }
  ],
  '_indices' => {
    'TYPE' => {
      'Mary' => 0
    }
  }
};
 
putKeyed( 'TYPE', { name => 'John' } )
# Now putKeyed so name 'John' added to 'Mary'
$meta = {
  'TYPE' => [
    {
      'name' => 'Mary'
    },
    {
      'name' => 'John'
    }
  ],
  '_indices' => {
    'TYPE' => {
      'John' => 1,
      'Mary' => 0
    }
  }
};
 
putKeyed( 'TYPE', { name => 'Bill' } )
# Now putKeyed so name 'Bill' added to 'Mary' and 'John'
# Note the sequence in indices is 'Mary', 'John', 'Bill' reflecting insertion order
$meta = {
  'TYPE' => [
    {
      'name' => 'Mary'
    },
    {
      'name' => 'John'
    },
    {
      'name' => 'Bill'
    }
  ],
  '_indices' => {
    'TYPE' => {
      'Bill' => 2,
      'John' => 1,
      'Mary' => 0
    }
  }
};
 
put( 'TYPE', { name => 'John' } )
# Now, inconsistently, we put rather than putKeyed
# This forces index 0 for 'John', but we get a gap in the indices
$meta = {
  'TYPE' => [
    {
      'name' => 'John'
    },
    {
      'name' => 'John'
    },
    {
      'name' => 'Bill'
    }
  ],
  '_indices' => {
    'TYPE' => {
      'Bill' => 2,
      'John' => 0
    }
  }
};
 
put( 'TYPE', { name => 'Mary' } )
# Now, inconsistently, we put rather than putKeyed
# 'Mary' replaces 'John' as index 0
$meta = {
  'TYPE' => [
    {
      'name' => 'Mary'
    },
    {
      'name' => 'John'
    },
    {
      'name' => 'Bill'
    }
  ],
  '_indices' => {
    'TYPE' => {
      'Bill' => 2,
      'Mary' => 0
    }
  }
};
 
 
--
Julian Levens
 

------------------------------------------------------------------------------
Full-scale, agent-less Infrastructure Monitoring from a single dashboard
Integrate with 40+ ManageEngine ITSM Solutions for complete visibility
Physical-Virtual-Cloud Infrastructure monitoring from one console
Real user monitoring with APM Insights and performance trend reports
Learn More http://pubads.g.doubleclick.net/gampad/clk?id=247754911&iu=/4140
_______________________________________________
Foswiki-discuss mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/foswiki-discuss
Reply | Threaded
Open this post in threaded view
|  
Report Content as Inappropriate

Re: Foswiki::META and 'many' syntax key

Belman Vadim
Thanks, this is about what I guessed about the situation myself. Well, legacy is a trouble like 8 out of 10 times and the only way to get rid of it just start floating to a new standard. In my view the declared plans of making it all built around some kind of Foswiki::TopicObject class would make this kind of thin possible but only if the new interface will drop all the backward compatibility pieces.

But it’s all about theory and I’m not well enough familiar with all the guts here. After all putAll() makes the job to me.

Yet another confusing issue I was hit by is about afterEditHandler and it’s $meta argument. It’s not documented other that within EmptyPlugin code so I consider it the official reference. First of all, it’s stated that "this handler is _not_ called unless the text is previewed" – not true, it's been called before saving a topic too. Yet, what's most confusing is that when it's called  before previewing the topic it's $meta argument is undef! Meanwhile it's also stated that "meta-data is _not_ embedded in the text passed to this handler".

To me it makes life especially difficult because I'm trying to drift away from embedding SQL and Perl code into a topic source by moving them into META and using registerTagHandler instead of relying on beforeCommonTagsHandler. Still I'd like to use embedding while the source is being edited. Adjusting topic's source with before/afterEditHandler works fine for simple editing and saving but fails for preview.

Belman Vadim





------------------------------------------------------------------------------
Full-scale, agent-less Infrastructure Monitoring from a single dashboard
Integrate with 40+ ManageEngine ITSM Solutions for complete visibility
Physical-Virtual-Cloud Infrastructure monitoring from one console
Real user monitoring with APM Insights and performance trend reports
Learn More http://pubads.g.doubleclick.net/gampad/clk?id=247754911&iu=/4140
_______________________________________________
Foswiki-discuss mailing list
[hidden email]
https://lists.sourceforge.net/lists/listinfo/foswiki-discuss
Loading...