Treex-PML
view release on metacpan or search on metacpan
lib/Treex/PML/Backend/FS.pm view on Meta::CPAN
v => { x => value_of_a/v/x,
y => value_of_a/v/y }
}
}>
In the PML schema emulation mode, it is forbidden to have both C<a>
and C<a/b> attributes. In such a case the parser reverts to
non-emulation mode.
=cut
$emulatePML=1;
sub test {
my ($f,$encoding)=@_;
if (ref($f) eq 'ARRAY') {
return $f->[0]=~/^@/;
} elsif (ref($f)) {
binmode $f unless UNIVERSAL::DOES::does($f,'IO::Zlib');
my $test = ($f->getline()=~/^@/);
return $test;
} else {
my $fh = open_backend($f,"r");
my $test = $fh && test($fh);
close_backend($fh);
return $test;
}
}
sub _fs2members {
my ($fs)=@_;
my $mbr = {};
my $defs = $fs->defs;
# sort, so that possible short parts go first
foreach my $attr (sort $fs->attributes) {
my $m = $mbr;
# check that no short attr exists
my @parts = split /\//,$attr;
my $short=$parts[0];
for (my $i=1;$i<@parts;$i++) {
if ($defs->{$short}) {
warn "Can't emulate PML schema: attribute name conflict between $short and $attr: falling back to non-emulation mode\n";
}
$short .= '/'.$parts[$i];
}
for my $part (@parts) {
$m->{structure}{member}{$part}{-name} = $part;
$m=$m->{structure}{member}{$part};
}
# allow ``alt'' values concatenated with |
if ($fs->isList($attr)) {
$m->{alt} = {
-flat => 1,
choice => [ $fs->listValues($attr) ]
};
} else {
$m->{alt} = {
-flat => 1,
cdata => { format =>'any' }
};
}
}
return $mbr->{structure}{member};
}
sub read {
my ($fileref,$fsfile) = @_;
return unless ref($fsfile);
my $FS = Treex::PML::Factory->createFSFormat();
$FS->readFrom($fileref) || return 0;
$fsfile->changeFS( $FS );
my $emu_schema_type;
if ($emulatePML) {
# fake a PML Schema:
my $members = _fs2members($fsfile->FS);
$members->{'#childnodes'}={
role => '#CHILDNODES',
list => {
ordered => 1,
type => 'fs-node.type',
},
};
my $node_type = {
name => 'fs-node',
role => '#NODE',
member => $members,
};
my $schema= Treex::PML::Schema->convert_from_hash({
description => 'PML schema generated from FS header',
root => { name => 'fs-data',
structure => {
member => {
trees => {
-name => 'trees',
role => '#TREES',
required => 1,
list => {
ordered => 1,
type => 'fs-node.type'
}
}
}
}
},
type => {
'fs-node.type' => {
-name => 'fs-node.type',
structure => $node_type,
}
}
});
if (defined($node_type->{member})) {
$emu_schema_type = $node_type;
$fsfile->changeMetaData('schema',$schema);
}
}
my ($root,$l,@rest);
( run in 1.546 second using v1.01-cache-2.11-cpan-524268b4103 )