Skip to content
Snippets Groups Projects
Commit ac62a4cc authored by Gerhard Gonter's avatar Gerhard Gonter :speech_balloon:
Browse files

converting content lines in parsend and array format back and forth seem to work now

parent 66295887
No related branches found
No related tags found
No related merge requests found
...@@ -4,10 +4,14 @@ package Tomboy::Note::Simple; ...@@ -4,10 +4,14 @@ package Tomboy::Note::Simple;
=head1 NAME =head1 NAME
Tomboy::Note::Simple; Tomboy::Note::Simple
=head1 SYNOPSIS =head1 SYNOPSIS
my $note= new Tomboy::Note::Simple (options => values);
=head2 parsing
# version 1 # version 1
my $n1= parse Tomboy::Note::Simple ($note_fnm); my $n1= parse Tomboy::Note::Simple ($note_fnm);
...@@ -19,7 +23,28 @@ package Tomboy::Note::Simple; ...@@ -19,7 +23,28 @@ package Tomboy::Note::Simple;
Simple abstraction for notes written with Gnome's Tomboy. Simple abstraction for notes written with Gnome's Tomboy.
The script uses XML::Parser in Tree style and uses it's parse The script uses XML::Parser in Tree style and uses it's parse
tree as the note's content datastructure. tree as the note's content datastructure (stored in "text").
=head1 BUGS
This module consists of originally two different ones, they are not
completely consistent. The difference is how the content is stored.
In a .note file, contents looks like this:
<text xml:space="preserve"><note-content version="0.1">title line
content line2
...
last content last</note-content></text>
* Parser: based on XML::Parser, stores contents in
@nc= @{$note->{'text'}->[2]} which represents the the <note-content>
element, the first text-part starts at $nc[2]
* Generator: contents (the stuff *in* the "note-content" element)
is put into "lines" the first line, however, is stored in 'title'.
That should be further unified.
=cut =cut
...@@ -30,40 +55,69 @@ use JSON; ...@@ -30,40 +55,69 @@ use JSON;
use Data::Dumper; use Data::Dumper;
$Data::Dumper::Indent= 1; $Data::Dumper::Indent= 1;
use Tomboy;
use Util::XML_Parser_Tree;
my %fields= my %fields=
( (
'title' => {}, 'title' => {},
'last-change-date' => {}, 'last-change-date' => {},
'last-metadata-change-date' => {}, 'last-metadata-change-date' => {},
'create-date' => {}, 'create-date' => {},
'cursor-position' => {}, 'cursor-position' => { 'default' => 0 },
'selection-bound-position' => {}, 'selection-bound-position' => { 'default' => -1, 'supress' => 1 },
'width' => {}, 'width' => { 'default' => 450 },
'height' => {}, 'height' => { 'default' => 360 },
'x' => {}, 'x' => { 'default' => 0 },
'y' => {}, 'y' => { 'default' => 0 },
'open-on-startup' => {}, 'open-on-startup' => { 'default' => 'False' },
); );
my @fields_date= qw( last-change-date last-metadata-change-date create-date );
my @fields_default1= qw( cursor-position selection-bound-position width height x y );
my @fields_default2= qw( open-on-startup );
my @fields_seq1= (@fields_date, @fields_default1);
my @fields_seq2= (@fields_default2);
my ($s_text, $e_text)= ('<text xml:space="preserve">', '</text>');
my ($s_note_content, $e_note_content)= ('<note-content version="0.1">', '</note-content>');
sub new sub new
{ {
my $class= shift; my $class= shift;
my %par= @_;
my $note= {}; my $title= 'New Note ' . Tomboy::ts_ISO ();
my $note=
{
'lines' => [ $title ],
'title' => $title,
};
foreach my $f (@fields_date) { $note->{$f}= Tomboy::ts_ISO() }
foreach my $f (@fields_default1) { $note->{$f}= $fields{'default'} }
bless $note, $class; bless $note, $class;
$note->set (@_);
foreach my $par (keys %par) $note;
{
$note->{$par}= $par{$par};
} }
$note; sub set
{
my $note= shift;
my %par= @_;
foreach my $par (keys %par) { $note->{$par}= $par{$par} }
1;
} }
=head1 Group1: Parsing
=cut
sub empty_text sub empty_text
{ {
my $note= shift; my $note= shift;
my $title= shift || 'empty text';
$note->{'text'}= [ $note->{'text'}= [
{ {
...@@ -75,9 +129,11 @@ sub empty_text ...@@ -75,9 +129,11 @@ sub empty_text
'version' => '0.1' 'version' => '0.1'
}, },
0, 0,
'empty text' $title,
] ]
]; ];
$note->{'title'}= $title;
$note->{'lines'}= [ $title ];
1; 1;
} }
...@@ -105,8 +161,16 @@ sub parse ...@@ -105,8 +161,16 @@ sub parse
my $p= new XML::Parser (Style => 'Tree'); my $p= new XML::Parser (Style => 'Tree');
# print "p: ", Dumper ($p); # print "p: ", Dumper ($p);
my $l1= $p->parsefile($fnm, ErrorContext => 3); my $l1;
eval { $l1= $p->parsefile($fnm, ErrorContext => 3) };
if ($@)
{
print "parsefile failed fnm=[$fnm]:\n", $@, "\n";
return undef;
}
# print "l1: ", Dumper ($l1); # print "l1: ", Dumper ($l1);
# my $s_l1= Util::XML_Parser_Tree::to_string (@$l1); print "s_l1=[$s_l1]\n";
my ($tag, $nc, @rest)= @$l1; my ($tag, $nc, @rest)= @$l1;
# print "res: ", Dumper ($res); # print "res: ", Dumper ($res);
...@@ -145,9 +209,18 @@ sub parse ...@@ -145,9 +209,18 @@ sub parse
if ($t1 eq '0') {} # skip text if ($t1 eq '0') {} # skip text
elsif ($t1 eq 'tag') elsif ($t1 eq 'tag')
{ {
# print "t2: [$t2]\n"; my $tag= $t2->[2];
push (@{$note->{'tags'}}, $t2->[2]); push (@{$note->{'tags'}}, $tag);
# ZZZ
if ($tag eq 'system:template')
{
$note->{'is_template'}= 1;
}
elsif ($tag =~ m#system:notebook:(.+)#)
{
$note->{'notebook'}= $1;
}
# TODO: maybe there other tags as well...
} }
} }
} }
...@@ -164,7 +237,186 @@ sub parse ...@@ -164,7 +237,186 @@ sub parse
$note; $note;
} }
=head1 Group 1+2: glue
=cut
sub text_to_lines
{
my $note= shift;
my $x= $note->{'text'};
# print "x: ", Dumper($x);
my $nc= $x->[2];
# print "nc: ", Dumper($nc);
shift (@$nc); # remove the text-element's attributes
my $s= Util::XML_Parser_Tree::to_string (@$nc);
# split drops the new lines at the end, so we need to go the extra mile
my $cnt= length ($1) if ($s=~ s#(\n+)$##);
my @s= split ("\n", $s);
for (my $i= 1; $i < $cnt; $i++) { push (@s, '') }
# print "complete string: [$s]\n";
# print "s: ", Dumper (\@s);
# print "cnt: ", $cnt, "\n";
my $title= $s[0];
# TODO: compare existing title
$note->{'title'}= $title unless ($note->{'title'});
$note->{'lines'}= \@s;
# ($title, @s);
1; 1;
}
sub parse_lines
{
my $note= shift;
# print "text: ", Dumper ($note->{'text'});
my @lines= @{$note->{'lines'}};
my $start= join ('', $s_text, $s_note_content, shift (@lines));
my $x= parse_string (join ("\n", $start, @lines, join ('', $e_note_content, $e_text)));
$note->{'text'}= $x->[1];
}
sub parse_string
{
my $str= shift;
# print "str=[$str]\n";
my $p= new XML::Parser (Style => 'Tree');
# print "p: ", Dumper ($p);
my $l1;
eval { $l1= $p->parsestring($str, ErrorContext => 3) };
if ($@)
{
print "parsestring failed str=[$str]:\n", $@, "\n";
return undef;
}
# print "l1: ", Dumper ($l1);
$l1;
}
=head1 Group 2: text generator
=cut
sub add_lines
{
my $note= shift;
foreach my $line (@_)
{
my @lines= split (/\n/, $line);
@lines= ('') unless (@lines);
# print "line=[$line] lines: ", main::Dumper (\@lines);
push (@{$note->{'lines'}}, @lines);
}
$note->{'e_updated'}= time();
}
sub save
{
my $note= shift;
my $out_dir= shift;
my $fnm_out= shift;
my ($title, $uuid, $ts_updated, $ts_md_updated, $ts_created, $e_updated, $lines, $is_template, $nb_name)=
map { $note->{$_} } qw(title uuid last-change-date last-metadata-change-date create-date e_updated lines is_template notebook);
# sanitize data
$note->{'uuid'}= $uuid= Tomboy::get_uuid() unless ($uuid);
$note->{'title'}= $title= $uuid unless ($title);
if ($e_updated)
{
$note->{'last-metadata-change-date'}= $ts_md_updated=
$note->{'last-change-date'}= $ts_updated= Tomboy::ts_ISO($e_updated);
}
$note->{'create-date'}= $ts_created= $ts_updated unless ($ts_created);
# print "tags: ", Dumper ($note->{'tags'});
my @tags= ();
push (@tags, 'system:template') if ($is_template);
push (@tags, 'system:notebook:'. $nb_name) if ($nb_name);
unless (defined ($fnm_out))
{
$fnm_out= $out_dir if ($out_dir);
$fnm_out.= $uuid . '.note';
}
unless (open (FO, '>:utf8', $fnm_out))
{
print STDERR "can't write to [$fnm_out]\n";
return undef;
}
print "writing note [$fnm_out]: [$title]\n"; # TODO: if verbose
print FO chr(65279); # write a BOM, Tomboy seems to like that
print FO <<EOX;
<?xml version="1.0" encoding="utf-8"?>
<note version="0.3" xmlns:link="http://beatniksoftware.com/tomboy/link" xmlns:size="http://beatniksoftware.com/tomboy/size" xmlns="http://beatniksoftware.com/tomboy">
EOX
print FO ' <title>'. Util::XML_Parser_Tree::tlt($title) ."</title>\n";
print FO ' ', $s_text, $s_note_content;
foreach my $line (@$lines)
{
print FO $line, "\n";
}
print FO $e_note_content, $e_text, "\n";
foreach my $f (@fields_seq1)
{
print_attribute (*FO, $note, $f);
}
if (@tags)
{
print FO " <tags>\n";
foreach my $tag (@tags) { print FO " <tag>", $tag, "</tag>\n"; }
print FO " </tags>\n";
}
foreach my $f (@fields_seq2)
{
print_attribute (*FO, $note, $f);
}
print FO "</note>"; # No newline at end of file, that's how Tomboy does that ...
close (FO);
$fnm_out;
}
sub print_attribute
{
local *F= shift;
my $n= shift;
my $f= shift;
my $a= $n->{$f};
unless (defined ($a))
{
my $x= $fields{$f};
return if (exists ($x->{'supress'})); # supress the default for that one
my $b;
if (exists ($x->{'default'})) { $b= $x->{'default'} }
# TODO: elsif exists function ....
$n->{$f}= $a= $b if (defined ($b));
}
print F ' <', $f, '>', $a, '</', $f, ">\n";
}
__END__ __END__
...@@ -174,7 +426,19 @@ __END__ ...@@ -174,7 +426,19 @@ __END__
=head1 BUGS =head1 BUGS
* XML::Parser throws exceptions, these are currently not handled. * XML::Parser throws exceptions, these are currently not handled well.
=cut =cut
<tags>
<tag>system:notebook:Kalender 2014</tag>
</tags>
Template:
<tags>
<tag>system:template</tag>
<tag>system:notebook:Kalender 2014</tag>
</tags>
1;
#!/usr/bin/perl #!/usr/bin/perl
=head1 NAME
s1.pl
=head1 DESCRIPTION
Script to play with Tomboy::Note::Simple for testing.
=cut
use strict; use strict;
use lib 'lib'; use lib 'lib';
...@@ -9,17 +19,49 @@ use Tomboy::Note::Simple; ...@@ -9,17 +19,49 @@ use Tomboy::Note::Simple;
use Data::Dumper; use Data::Dumper;
$Data::Dumper::Indent= 1; $Data::Dumper::Indent= 1;
my $note_fnm= shift (@ARGV); die "no note filename specified" unless (@ARGV);
open (FO, '>:utf8', 'do_verify.sh');
while (my $arg= shift (@ARGV))
{
process_note ($arg);
}
close (FO);
exit (0);
sub process_note
{
my $note_fnm= shift;
die "no note filename specified" unless ($note_fnm); print '='x90, "\n";
print "process_note note_fnm=[$note_fnm]\n";
# V1: # V1:
# my $n= parse Tomboy::Note::Simple ($note_fnm); my $n= parse Tomboy::Note::Simple ($note_fnm);
# V2: # V2:
my $n= new Tomboy::Note::Simple; $n->parse ($note_fnm); # my $n= new Tomboy::Note::Simple; $n->parse ($note_fnm);
print "n: ", Dumper ($n); $n->text_to_lines ();
# print "lines: ", Dumper ($n->{'lines'});
$n->parse_lines ();
# print "n: ", Dumper ($n);
my $saved= $n->save();
print "saved=[$saved]\n";
my @cmd= ('diff', '-u', $note_fnm, $saved);
print join (' ', @cmd), "\n";
my $rc= system (@cmd);
print "rc=[$rc]\n\n";
if ($rc != 0)
{
print FO join (' ', @cmd), "\n";
}
$rc;
}
exit (0);
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment