File Coverage

blib/lib/RDF/AllegroGraph/Session4.pm
Criterion Covered Total %
statement 24 102 23.5
branch 0 14 0.0
condition n/a
subroutine 8 25 32.0
pod 5 16 31.2
total 37 157 23.5


line stmt bran cond sub pod time code
1             package RDF::AllegroGraph::Session4;
2              
3 15     15   81 use strict;
  15         31  
  15         536  
4 15     15   75 use warnings;
  15         29  
  15         420  
5              
6 15     15   73 use base qw(RDF::AllegroGraph::Repository4);
  15         25  
  15         1375  
7              
8 15     15   79 use Data::Dumper;
  15         2065  
  15         807  
9 15     15   83 use feature "switch";
  15         32  
  15         1021  
10              
11 15     15   87 use JSON;
  15         27  
  15         92  
12 15     15   2398 use URI::Escape qw/uri_escape_utf8/;
  15         31  
  15         761  
13              
14 15     15   78 use HTTP::Request::Common;
  15         30  
  15         24576  
15              
16             =pod
17              
18             =head1 NAME
19              
20             RDF::AllegroGraph::Session4 - AllegroGraph session handle for AGv4
21              
22             =head1 INTERFACE
23              
24             =cut
25              
26             sub new {
27 0     0 0   my $class = shift;
28 0           return bless { @_ }, $class;
29             }
30              
31             =pod
32              
33             =head2 Methods (additional to L)
34              
35             =over
36              
37             =item B
38              
39             I<$pong> = I<$session>->ping
40              
41             This method will keep the "connection" with the HTTP server alive (it probably resets the
42             timeout). In the regular case it should return C, in the error case it will time out.
43              
44             =cut
45              
46             sub ping {
47 0     0 1   my $self = shift;
48 0           my $resp = $self->{CATALOG}->{SERVER}->{ua}->get ($self->{path} . '/session/ping');
49 0 0         die "protocol error: ".$resp->status_line.' ('.$resp->content.')' unless $resp->is_success;
50 0           my $result = $resp->content;
51 0           $result =~ s/^\"//; $result =~ s/\"$//;
  0            
52 0           return $result;
53             }
54              
55             =pod
56              
57             =item B
58              
59             I<$session>->rules (" .... prolog rules encoded in LISP, brr ...")
60              
61             This method parks additional I as rules onto the server. If they can be
62             parsed correctly, they will be used with the onboard PROLOG reasoner. See the Franz Prolog tutorial
63             (./doc/prolog-tutorial.html) for details.
64              
65             =cut
66              
67             sub rules {
68 0     0 1   my $self = shift;
69 0           my $lisp = shift;
70 0           my $resp = $self->{CATALOG}->{SERVER}->{ua}->post ($self->{path} . '/functor',
71             'Content-Type' => 'text/plain', 'Content' => $lisp);
72 0 0         die "protocol error: ".$resp->status_line.' ('.$resp->content.')' unless $resp->is_success;
73             }
74              
75             =pod
76              
77             =item B
78              
79             This method creates one I, in the AGv4 sense. As parameter you have to
80             pass in
81              
82             =over
83              
84             =item the name of the generator:
85              
86             A symbol, just a simple string, probably better without any fancy characters.
87              
88             =item how to reach other nodes in the RDF model:
89              
90             Here you name various predicates (full URIs, no namespaces seem to work) and also whether
91             these edges should be followed
92              
93             =over
94              
95             =item in the C direction, or
96              
97             =item in the C direction (I in the OWL sense), or
98              
99             =item in both directions: C
100              
101             =back
102              
103             =back
104              
105             Example:
106              
107             $session->generator ('associates',
108             { '' => 'bidirectional',
109             '' => 'bidirectional' }
110             );
111              
112             =cut
113              
114             sub generator {
115 0     0 1   my $self = shift;
116 0           my $symbol = shift;
117 0           my $spec = shift;
118              
119 0           my @bidirectional;
120             my @forward;
121 0           my @reverse;
122 0           foreach my $pred (keys %$spec) {
123 0           given ($spec->{$pred}) {
124 0           when ('bidirectional') {
125 0           push @bidirectional, $pred;
126             }
127 0           when ('forward') {
128 0           push @forward, $pred;
129             }
130 0           when ('reverse') {
131 0           push @reverse, $pred;
132             }
133             }
134             }
135             # warn Dumper \@undirected;
136              
137 0           my $url = new URI ($self->{path} . '/snaGenerators/' . $symbol);
138 0 0         $url->query_form (
    0          
    0          
139             (@bidirectional ? (undirected => \@bidirectional) : ()),
140             (@forward ? (objectOf => \@forward) : ()),
141             (@reverse ? (subjectOf => \@reverse) : ()),
142             );
143              
144 0           my $resp = $self->{CATALOG}->{SERVER}->{ua}->request (PUT $url);
145 0 0         die "protocol error: ".$resp->status_line.' ('.$resp->content.')' unless $resp->is_success;
146             }
147              
148             =pod
149              
150             =back
151              
152             =head2 SNA Convenience Methods
153              
154             While all of the following can be (and actually are) emulated via C and C
155             invocations, you might find the following handy:
156              
157             =over
158              
159             =item B
160              
161             I<@members> = I<$session>->SNA_members (I<$start_node>, { I })
162              
163             This method returns the member nodes which can be reached when starting at a particular node and
164             when particular edges are followed. That edge specification is the same as for the method
165             C.
166              
167             B: Internally an SNA generator is created and - using this method - it will be always
168             overwritten. So, if you need to query this heavily, it is better to fall back to the low-level
169             generator method and use that instead of a full specification:
170              
171             $session->generator ('intimates',
172             { '' => 'bidirectional' });
173              
174             @ms = $session->SNA_members ('', 'intimates');
175              
176             =cut
177              
178             our $adhoc = 'zwumpelfax'; # you may change it, but under what circumstances, really?
179              
180             sub _linkage {
181 0     0     my $self = shift;
182 0           my $spec = shift;
183              
184 0 0         if (ref ($spec) eq 'HASH') {
185 0           my $linkage = $adhoc;
186 0           $self->generator ($linkage, $spec);
187 0           return $linkage;
188             } else {
189 0           return $spec; # it is already a string
190             }
191             }
192              
193             sub SNA_members {
194 0     0 1   my $self = shift;
195 0           my $start = shift;
196 0           my $spec = shift;
197              
198 0           my $linkage = _linkage ($self, $spec);
199 0           my @ss = $self->prolog (qq{
200             (select (?member)
201             (ego-group-member !$start 1 $linkage ?member)
202             )
203             });
204             # warn Dumper \@ss;
205 0           return map {$_->[0] } @ss;
  0            
206             }
207              
208             sub SNA_ego_group {
209 0     0 0   my $self = shift;
210 0           my $start = shift;
211 0           my $spec = shift;
212 0           my $depth = shift;
213              
214 0           return ();
215             }
216              
217             sub SNA_path {
218 0     0 0   my $self = shift;
219 0           my $start = shift;
220 0           my $stop = shift;
221 0           my $spec = shift;
222 0           my $depth = shift;
223              
224 0           my $linkage = _linkage ($self, $spec);
225 0           my @ss = $self->prolog (qq{
226             (select (?path)
227             (breadth-first-search-path !$start !$stop $linkage $depth ?path))
228             });
229 0           warn "ss ". Dumper \@ss;
230 0           return map { $_->[0] } @ss;
  0            
231             }
232              
233             # strategy : breadth_first, depth_first, bidirectional
234              
235             sub SNA_nodal_degree {
236 0     0 0   my $self = shift;
237 0           my $node = shift;
238 0           my $spec = shift;
239              
240             }
241              
242             sub SNA_nodal_neighbors {
243 0     0 0   my $self = shift;
244 0           my $node = shift;
245 0           my $spec = shift;
246             }
247              
248             =pod
249              
250             =item B
251              
252             I<@cliques> = I<$session>->SNA_cliques (I<$node>, I<$generator>)
253              
254             This method returns a list of list references to the cliques the node is part of. The generator can
255             again be one predefined (see C), or an adhoc one (see C).
256              
257             =cut
258              
259             sub SNA_cliques {
260 0     0 1   my $self = shift;
261 0           my $node = shift;
262 0           my $spec = shift;
263              
264 0           my $linkage = _linkage ($self, $spec);
265 0           my @ss = $self->prolog (qq{
266             (select (?clique)
267             (clique !$node $linkage ?clique))
268             });
269             # warn Dumper \@ss;
270 0           return map { $_->[0] } @ss;
  0            
271             }
272              
273 0     0 0   sub SNA_actor_degree_centrality {
274             }
275              
276 0     0 0   sub SNA_actor_closeness_centrality {
277             }
278              
279 0     0 0   sub SNA_actor_betweeness_centrality {
280             }
281              
282 0     0 0   sub SNA_group_degree_centrality {
283             }
284              
285 0     0 0   sub SNA_group_closeness_centrality {
286             }
287              
288 0     0 0   sub SNA_group_betweeness_centrality {
289             }
290              
291              
292              
293             =pod
294              
295             =back
296              
297             =head1 AUTHOR
298              
299             Robert Barta, C<< >>
300              
301             =head1 COPYRIGHT & LICENSE
302              
303             Copyright 2011 Robert Barta, all rights reserved.
304              
305             This program is free software; you can redistribute it and/or modify it under the same terms as Perl
306             itself.
307              
308             L
309              
310             =cut
311              
312             our $VERSION = '0.03';
313              
314             1;
315              
316             __END__