/[A3C]/lib/A3C/LDAP.pm
This is repository of my old source code which isn't updated any more. Go to git.rot13.org for current projects!
ViewVC logotype

Diff of /lib/A3C/LDAP.pm

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 41 by dpavlin, Sun Mar 30 15:23:35 2008 UTC revision 181 by dpavlin, Mon Jun 16 20:08:28 2008 UTC
# Line 6  use warnings; Line 6  use warnings;
6  use Net::LDAP;  use Net::LDAP;
7  use Data::Dump qw/dump/;  use Data::Dump qw/dump/;
8  use base qw(Jifty::Object Class::Accessor::Fast);  use base qw(Jifty::Object Class::Accessor::Fast);
9  __PACKAGE__->mk_accessors( qw(ldap server dn password current_search) );  use Jifty;
10    our @config_fields = keys %{ Jifty->config->app('LDAP') };
11    Jifty->log->debug("using fields from configuration: ",dump( @config_fields ));
12    __PACKAGE__->mk_accessors( qw(ldap current_search), @config_fields );
13    
14    
15  =head1 NAME  =head1 NAME
# Line 34  sub new { Line 37  sub new {
37          my $ldap_config = Jifty->config->app('LDAP');          my $ldap_config = Jifty->config->app('LDAP');
38          Jifty->log->debug( "config->app(LDAP) = ",dump( $ldap_config ) );          Jifty->log->debug( "config->app(LDAP) = ",dump( $ldap_config ) );
39    
40          $args->{server}         ||= $ldap_config->{Server};          foreach my $f ( @config_fields ) {
41          $args->{dn}                     ||= $ldap_config->{DN};                  if ( my $v = $ldap_config->{$f} ) {
42          $args->{password}       ||= $ldap_config->{Password};                          $args->{$f} = $v;
43                    }
44            }
45    
46            # configuration sanity testing
47            foreach ( qw/server dn password base objectClass link/ ) {
48                    die "missing required field $_ in LDAP from etc/config.yaml" unless $args->{$_};
49            }
50            foreach ( qw/person organization/ ) {
51                    die "missing required field $_ in LDAP.objectClass.$_ from etc/config.yaml" unless $args->{objectClass}->{$_};
52            }
53            foreach ( qw/person_filter display_from value_from/ ) {
54                    die "missing required field $_ in LDAP.link.$_ from etc/config.yaml" unless $args->{link}->{$_};
55            }
56    
57          my $ldap = Net::LDAP->new( $args->{server} ) or die "$@";          my $ldap = Net::LDAP->new( $args->{server} ) or die "$@";
58    
# Line 54  sub new { Line 70  sub new {
70  =head2 search  =head2 search
71    
72    my $msg = A3C::LDAP->search(    my $msg = A3C::LDAP->search(
73                          base    => 'dc=skole,dc=hr',          base    => 'dc=skole,dc=hr',
74                          filter  => '(objectClass=hrEduOrg)',          filter  => '(objectClass=hrEduOrg)',
75                          sizelimit => 10,          sizelimit => 10,
76    );    );
77    
78  =cut  =cut
# Line 66  sub search { Line 82  sub search {
82    
83          my $search = $self->ldap->search( @_ );          my $search = $self->ldap->search( @_ );
84          if ( $search->code != 0 ) {          if ( $search->code != 0 ) {
85                  Jifty->log->error( $search->error );                  Jifty->log->error( $search->error, ' for ', dump( @_ ) );
86          }          }
87          return $self->current_search( $search );          return $self->current_search( $search );
88  }  }
# Line 98  sub count { Line 114  sub count {
114          $self->current_search->count;          $self->current_search->count;
115  }  }
116    
117    =head2 collection
118    
119      my $connection = $ldap->collection(
120            # name of model to use
121            $ldap->objectClass->{organization},
122            # optional params
123            limit => $limit,
124            filter => '(uid=foobar)',
125      );
126    
127    =cut
128    
129    my $collection2filter = {
130            'Person'                => '(objectClass=hrEduPerson)',
131            'Organization'  => '(objectClass=hrEduOrg)',
132    };
133    
134    sub collection {
135            my $self = shift;
136            my $model = shift or die "no model?";
137            my $args = {@_};
138    
139            $args->{limit} ||= 0;   # unlimited by default
140    
141            my $filter = $collection2filter->{$model};
142    #       die "unknown model $model" unless $filter;
143            # fallback to model named as objectClass
144            $filter ||= "(objectClass=$model)";
145    
146            # add user filter
147            $filter = '(&' . $filter . $args->{filter} . ')' if $args->{filter};
148    
149            $self->search(
150                    base => $self->base,
151                    filter => $filter,
152                    sizelimit => $args->{limit},
153            );
154    
155            Jifty->log->info(
156                    "Searching LDAP for $model with $filter ",
157                    $args->{limit} ? 'limit ' . $args->{limit} . ' ' : '',
158                    'returned ', $self->count, ' results'
159            );
160    
161            my $class = Jifty->app_class('Model', $model . 'Collection' ) or die "can't create ${model}Collection";
162            my $collection = $class->new() or die "can't $class->new";
163    
164            while ( my $entry = $self->next ) {
165                    my $model_obj = Jifty->app_class('Model',$model)->new;
166                    my $additional;
167                    $self->model_from_entry( $model_obj, $entry, %$additional );
168                    $collection->add_record( $model_obj );
169            }
170    
171            return $collection;
172    }
173    
174  =head1 INTERNAL METHODS  =head1 INTERNAL METHODS
175    
176  Following methods map directly into L<Net::LDAP>  Following methods map directly into L<Net::LDAP>
# Line 106  Following methods map directly into L<Ne Line 179  Following methods map directly into L<Ne
179    
180  Result of last C<< $ldap->search >> request  Result of last C<< $ldap->search >> request
181    
182    =head2 model_from_entry
183    
184      $ldap->model_from_entry( $model, $entry, $additional );
185    
186    This method will join repeatable attributes by magic marker,
187    see C<XXX> in code!
188    
189  =cut  =cut
190    
191    sub model_from_entry {
192            my ( $self, $model, $entry, $additional ) = @_;
193            my $data;
194    
195            my @columns = map { $_->name } $model->columns;
196            #warn "# columns = ",dump( @columns );
197    
198            foreach my $attr ( $entry->attributes ) {
199                    if ( grep(/^\Q$attr\E$/, @columns ) ) {
200    #                       $data->{$attr} = $entry->get_value( $attr );
201                            my @var = $entry->get_value( $attr );
202    #                       warn "--- $attr = ",dump( @var );
203                            # XXX this rolls repeatable values into single field
204                            my $var = join(' <*> ', @var);
205                            $data->{$attr} = $var;
206    #               } elsif ( $attr !~ m/^(objectClass)$/i ) {
207                    } else {
208                            Jifty->log->warn(ref($model)," doesn't have $attr");
209                    }
210            }
211    
212            Jifty->log->debug( ref($model), ' = ', dump( $data ) );
213    
214            my ( $id, $message ) = $model->load_or_create( %$data, %$additional );
215    
216            if ( $id ) {
217                    Jifty->log->info( $message || 'Added', ' ', ref($model), ' ', $model->id, ' ', $model->name );
218            } else {
219                    Jifty->log->error( ref($model), " ", $message );
220            }
221    }
222    
223    
224    
225  1;  1;

Legend:
Removed from v.41  
changed lines
  Added in v.181

  ViewVC Help
Powered by ViewVC 1.1.26