summaryrefslogtreecommitdiff
path: root/FS/FS/part_export/communigate_pro.pm
diff options
context:
space:
mode:
authorivan <ivan>2010-02-20 22:34:57 +0000
committerivan <ivan>2010-02-20 22:34:57 +0000
commitd2e5d9d1f65fc94eb87eae45b675645e92087f49 (patch)
tree30919f1acbc7e290efb1b48b5ed6315cafbcff39 /FS/FS/part_export/communigate_pro.pm
parenta5288a7f85b5c494821133c692fc8b5ced84abcf (diff)
communigate pro provisioning, RT#7083
Diffstat (limited to 'FS/FS/part_export/communigate_pro.pm')
-rw-r--r--FS/FS/part_export/communigate_pro.pm377
1 files changed, 274 insertions, 103 deletions
diff --git a/FS/FS/part_export/communigate_pro.pm b/FS/FS/part_export/communigate_pro.pm
index c4201c0..90283d2 100644
--- a/FS/FS/part_export/communigate_pro.pm
+++ b/FS/FS/part_export/communigate_pro.pm
@@ -1,7 +1,7 @@
package FS::part_export::communigate_pro;
use strict;
-use vars qw(@ISA %info %options $DEBUG);
+use vars qw(@ISA %info %options %quotas $DEBUG);
use Data::Dumper;
use Tie::IxHash;
use FS::part_export;
@@ -15,7 +15,7 @@ tie %options, 'Tie::IxHash',
'port' => { label =>'Port number', default=>'106', },
'login' => { label =>'The administrator account name. The name can contain a domain part.', },
'password' => { label =>'The administrator account password.', },
- 'accountType' => { label => 'Type for newly-created accounts',
+ 'accountType' => { label => 'Type for newly-created accounts (default when not specified in service)',
type => 'select',
options => [qw(MultiMailbox TextMailbox MailDirMailbox)],
default => 'MultiMailbox',
@@ -23,7 +23,7 @@ tie %options, 'Tie::IxHash',
'externalFlag' => { label => 'Create accounts with an external (visible for legacy mailers) INBOX.',
type => 'checkbox',
},
- 'AccessModes' => { label => 'Access modes',
+ 'AccessModes' => { label => 'Access modes (default when not specified in service)',
default => 'Mail POP IMAP PWD WebMail WebSite',
},
'create_domain' => { label => 'Domain creation API call',
@@ -33,7 +33,7 @@ tie %options, 'Tie::IxHash',
;
%info = (
- 'svc' => [qw( svc_acct svc_domain )],
+ 'svc' => [qw( svc_acct svc_domain svc_forward )],
'desc' => 'Real-time export of accounts and domains to a CommuniGate Pro mail server',
'options' => \%options,
'notes' => <<'END'
@@ -45,6 +45,13 @@ must be installed as CGP::CLI.
END
);
+%quotas = (
+ 'quota' => 'MaxAccountSize',
+ 'file_quota' => 'MaxWebSize',
+ 'file_maxnum' => 'MaxWebFiles',
+ 'file_maxsize' => 'MaxFileSize',
+);
+
sub rebless { shift; }
sub export_username {
@@ -55,164 +62,318 @@ sub export_username {
sub _export_insert {
my( $self, $svc_x ) = (shift, shift);
- my @options;
+ my $table = $svc_x->table;
+ my $method = "_export_insert_$table";
+ $self->$method($svc_x, @_);
+}
- if ( $svc_x->isa('FS::svc_acct') ) {
+sub _export_insert_svc_acct {
+ my( $self, $svc_acct ) = (shift, shift);
+
+ my @options = ( $svc_acct->svcnum, 'CreateAccount',
+ 'accountName' => $self->export_username($svc_acct),
+ 'accountType' => ( $svc_acct->cgp_type
+ || $self->option('accountType') ),
+ 'AccessModes' => ( $svc_acct->cgp_accessmodes
+ || $self->option('AccessModes') ),
+ 'RealName' => $svc_acct->finger,
+ 'Password' => $svc_acct->_password,
+ );
- @options = ( $svc_x->svcnum, 'CreateAccount',
- 'accountName' => $self->export_username($svc_x),
- 'accountType' => $self->option('accountType'),
- 'AccessModes' => $self->option('AccessModes'),
- 'RealName' => $svc_x->finger,
- 'Password' => $svc_x->_password,
- );
- push @options, 'MaxAccountSize' => $svc_x->quota if $svc_x->quota;
- push @options, 'externalFlag' => $self->option('externalFlag')
- if $self->option('externalFlag');
+ push @options, $quotas{$_} => $svc_acct->$_()
+ foreach grep $svc_acct->$_(), keys %quotas;
- } elsif ( $svc_x->isa('FS::svc_domain') ) {
+ #phase 2: pwdallowed, passwordrecovery, allowed mail rules,
+ # RPOP modifications, accepts mail to all, add trailer to sent mail
+ #phase 3: archive messages, mailing lists
- my $create = $self->option('create_domain') || 'CreateDomain';
+ push @options, 'externalFlag' => $self->option('externalFlag')
+ if $self->option('externalFlag');
- @options = ( $svc_x->svcnum, $create, $svc_x->domain,
- #other domain creation options?
- );
- push @options, 'AccountsLimit' => $svc_x->max_accounts
- if $svc_x->max_accounts;
+ #XXX preferences phase 1: message delete method, on logout remove trash
+ #phase 2: language, time zone, layout, pronto style, send read receipts
- } else {
- die "guru meditation #14: $svc_x is not FS::svc_acct, or FS::svc_domain";
- }
+ $self->communigate_pro_queue( @options );
+
+}
+
+sub _export_insert_svc_domain {
+ my( $self, $svc_domain ) = (shift, shift);
+
+ my $create = $self->option('create_domain') || 'CreateDomain';
+
+ my @options = ( $svc_domain->svcnum, $create, $svc_domain->domain,
+ #other domain creation options?
+ );
+ push @options, 'AccountsLimit' => $svc_domain->max_accounts
+ if $svc_domain->max_accounts;
$self->communigate_pro_queue( @options );
}
+#sub _export_insert_svc_forward {
+#}
+
sub _export_replace {
my( $self, $new, $old ) = (shift, shift, shift);
- if ( $new->isa('FS::svc_acct') ) {
-
- #XXX they probably need the ability to change some of these
- return "can't (yet) change username with CommuniGate Pro"
- if $old->username ne $new->username;
- return "can't (yet) change domain with CommuniGate Pro"
- if $self->export_username($old) ne $self->export_username($new);
- return "can't (yet) change GECOS with CommuniGate Pro"
- if $old->finger ne $new->finger;
- return "can't (yet) change quota with CommuniGate Pro"
- if $old->quota ne $new->quota;
- return '' unless $old->username ne $new->username
- || $old->_password ne $new->_password
- || $old->finger ne $new->finger
- || $old->quota ne $new->quota;
-
- return '' if '*SUSPENDED* '. $old->_password eq $new->_password;
-
- #my $err_or_queue = $self->communigate_pro_queue( $new->svcnum,'RenameAccount',
- # $old->email, $new->email );
- #return $err_or_queue unless ref($err_or_queue);
- #my $jobnum = $err_or_queue->jobnum;
+ my $table = $new->table;
+ my $method = "_export_replace_$table";
+ $self->$method($new, $old, @_);
+}
+
+sub _export_replace_svc_acct {
+ my( $self, $new, $old ) = (shift, shift, shift);
+ #let's just do the rename part realtime rather than trying to queue
+ #w/dependencies. we don't want FS winding up out-of-sync with the wrong
+ #username and a queued job anyway. right??
+ if ( $self->export_username($old) ne $self->export_username($new) ) {
+ #my $r =
+ eval { $self->communigate_pro_runcommand(
+ 'RenameAccount',
+ $self->export_username($old),
+ $self->export_username($new),
+ ) };
+ return $@ if $@;
+ }
+
+ if ( $new->_password ne $old->_password
+ && '*SUSPENDED* '.$old->_password ne $new->_password
+ ) {
$self->communigate_pro_queue( $new->svcnum, 'SetAccountPassword',
- $self->export_username($new), $new->_password )
- if $new->_password ne $old->_password;
+ $self->export_username($new), $new->_password
+ );
+ }
- } elsif ( $new->isa('FS::svc_domain') ) {
+ my %settings = ();
+
+ $settings{'RealName'} = $new->finger
+ if $old->finger ne $new->finger;
+ $settings{$quotas{$_}} = $new->$_()
+ foreach grep $old->$_() ne $new->$_(), keys %quotas;
+ $settings{'AccessModes'} = $new->cgp_accessmodes
+ if $old->cgp_accessmodes ne $new->cgp_accessmodes;
+ $settings{'accountType'} = $new->cgp_type
+ if $old->cgp_type ne $new->cgp_type;
+
+ #phase 2: pwdallowed, passwordrecovery, allowed mail rules,
+ # RPOP modifications, accepts mail to all, add trailer to sent mail
+ #phase 3: archive messages, mailing lists
+
+ if ( keys %settings ) {
+ my $error = $self->communigate_pro_queue(
+ $new->svcnum,
+ 'UpdateAccountSettings',
+ $self->export_username($new),
+ %settings,
+ );
+ return $error if $error;
+ }
- if ( $old->domain ne $new->domain ) {
- $self->communigate_pro_queue( $new->svcnum, 'RenameDomain',
- $old->domain, $new->domain,
- );
- }
+ #XXX preferences phase 1: message delete method, on logout remove trash
+ #phase 2: language, time zone, layout, pronto style, send read receipts
- if ( $old->max_accounts ne $new->max_accounts ) {
- $self->communigate_pro_queue( $new->svcnum, 'UpdateDomainSettings',
- $new->domain, 'AccountsLimit' => ($new->max_accounts || 'default'),
- );
- }
+ '';
+
+}
- #other kinds of changes?
+sub _export_replace_svc_domain {
+ my( $self, $new, $old ) = (shift, shift, shift);
+
+ if ( $old->domain ne $new->domain ) {
+ my $error = $self->communigate_pro_queue( $new->svcnum, 'RenameDomain',
+ $old->domain, $new->domain,
+ );
+ return $error if $error;
+ }
- } else {
- die "guru meditation #15: $new is not FS::svc_acct, or FS::svc_domain";
+ if ( $old->max_accounts ne $new->max_accounts ) {
+ my $error = $self->communigate_pro_queue( $new->svcnum,
+ 'UpdateDomainSettings',
+ $new->domain,
+ 'AccountsLimit' => ($new->max_accounts || 'default'),
+ );
+ return $error if $error;
}
+ #other kinds of changes?
+
+ '';
}
sub _export_delete {
my( $self, $svc_x ) = (shift, shift);
- if ( $svc_x->isa('FS::svc_acct') ) {
+ my $table = $svc_x->table;
+ my $method = "_export_delete_$table";
+ $self->$method($svc_x, @_);
+}
- $self->communigate_pro_queue( $svc_x->svcnum, 'DeleteAccount',
- $self->export_username($svc_x),
- );
+sub _export_delete_svc_acct {
+ my( $self, $svc_acct ) = (shift, shift);
- } elsif ( $svc_x->isa('FS::svc_domain') ) {
+ $self->communigate_pro_queue( $svc_acct->svcnum, 'DeleteAccount',
+ $self->export_username($svc_acct),
+ );
- $self->communigate_pro_queue( $svc_x->svcnum, 'DeleteDomain',
- $svc_x->domain,
- #XXX turn on force option for domain deletion?
- );
+}
- } else {
- die "guru meditation #16: $svc_x is not FS::svc_acct, or FS::svc_domain";
- }
+sub _export_delete_svc_domain {
+ my( $self, $svc_domain ) = (shift, shift);
+
+ $self->communigate_pro_queue( $svc_domain->svcnum, 'DeleteDomain',
+ $svc_domain->domain,
+ #XXX turn on force option for domain deletion?
+ );
}
sub _export_suspend {
my( $self, $svc_x ) = (shift, shift);
- if ( $svc_x->isa('FS::svc_acct') ) {
+ my $table = $svc_x->table;
+ my $method = "_export_suspend_$table";
+ $self->$method($svc_x, @_);
- $self->communigate_pro_queue( $svc_x->svcnum, 'UpdateAccountSettings',
- 'accountName' => $self->export_username($svc_x),
- 'AccessModes' => 'Mail',
- );
+}
- } elsif ( $svc_x->isa('FS::svc_domain') ) {
+sub _export_suspend_svc_acct {
+ my( $self, $svc_acct ) = (shift, shift);
- #XXX domain operations
- } else {
- die "guru meditation #17: $svc_x is not FS::svc_acct, or FS::svc_domain";
- }
+ #XXX is this the desired suspnsion action?
+
+ $self->communigate_pro_queue(
+ $svc_acct->svcnum,
+ 'UpdateAccountSettings',
+ $self->export_username($svc_acct),
+ 'AccessModes' => 'Mail',
+ );
+
+}
+
+sub _export_suspend_svc_domain {
+ my( $self, $svc_domain) = (shift, shift);
+
+ #XXX domain operations
+ '';
}
sub _export_unsuspend {
my( $self, $svc_x ) = (shift, shift);
- if ( $svc_x->isa('FS::svc_acct') ) {
+ my $table = $svc_x->table;
+ my $method = "_export_unsuspend_$table";
+ $self->$method($svc_x, @_);
- $self->communigate_pro_queue( $svc_x->svcnum, 'UpdateAccountSettings',
- 'accountName' => $self->export_username($svc_x),
- 'AccessModes' => $self->option('AccessModes'),
- );
- } elsif ( $svc_x->isa('FS::svc_domain') ) {
+}
- #XXX domain operations
- } else {
- die "guru meditation #18: $svc_x is not FS::svc_acct, or FS::svc_domain";
- }
+sub _export_unsuspend_svc_acct {
+ my( $self, $svc_acct ) = (shift, shift);
+
+ $self->communigate_pro_queue(
+ $svc_acct->svcnum,
+ 'UpdateAccountSettings',
+ $self->export_username($svc_acct),
+ 'AccessModes' => $self->option('AccessModes'),
+ );
+
+}
+
+sub _export_unsuspend_svc_domain {
+ my( $self, $svc_domain) = (shift, shift);
+
+ #XXX domain operations
+ '';
}
+
sub export_getsettings {
- my($self, $svc_x, $settingsref, $defaultref ) = @_;
+ my($self, $svc_x) = (shift, shift);
+
+ my $table = $svc_x->table;
+ my $method = "export_getsettings_$table";
+
+ $self->can($method) ? $self->$method($svc_x, @_) : '';
+
+}
+
+sub export_getsettings_svc_domain {
+ my($self, $svc_domain, $settingsref, $defaultref ) = @_;
my $settings = eval { $self->communigate_pro_runcommand(
'GetDomainSettings',
- $svc_x->domain
+ $svc_domain->domain
) };
return $@ if $@;
my $effective_settings = eval { $self->communigate_pro_runcommand(
'GetDomainEffectiveSettings',
- $svc_x->domain
+ $svc_domain->domain
+ ) };
+ return $@ if $@;
+
+ my $acct_defaults = eval { $self->communigate_pro_runcommand(
+ 'GetAccountDefaults',
+ $svc_domain->domain
+ ) };
+ return $@ if $@;
+
+ #warn Dumper($acct_defaults);
+
+ %$effective_settings = ( %$effective_settings,
+ map { ("Acct. Default $_" => $acct_defaults->{$_}); }
+ keys(%$acct_defaults)
+ );
+
+ #false laziness w/below
+
+ my %defaults = map { $_ => 1 }
+ grep !exists(${$settings}{$_}), keys %$effective_settings;
+
+ foreach my $key ( grep ref($effective_settings->{$_}),
+ keys %$effective_settings )
+ {
+ my $value = $effective_settings->{$key};
+ if ( ref($value) eq 'ARRAY' ) {
+ $effective_settings->{$key} = join(', ', @$value);
+ } else {
+ #XXX
+ warn "serializing ". ref($value). " for table display not yet handled";
+ }
+ }
+
+ %{$settingsref} = %$effective_settings;
+ %{$defaultref} = %defaults;
+
+ '';
+}
+
+sub export_getsettings_svc_acct {
+ my($self, $svc_acct, $settingsref, $defaultref ) = @_;
+
+ my $settings = eval { $self->communigate_pro_runcommand(
+ 'GetAccountSettings',
+ $svc_acct->email
) };
return $@ if $@;
+ delete($settings->{'Password'});
+
+ my $effective_settings = eval { $self->communigate_pro_runcommand(
+ 'GetAccountEffectiveSettings',
+ $svc_acct->email
+ ) };
+ return $@ if $@;
+
+ delete($effective_settings->{'Password'});
+
+ #XXX prefs/effectiveprefs too
+
+ #false laziness w/above
+
my %defaults = map { $_ => 1 }
grep !exists(${$settings}{$_}), keys %$effective_settings;
@@ -232,10 +393,18 @@ sub export_getsettings {
%{$defaultref} = %defaults;
'';
+
}
sub communigate_pro_queue {
my( $self, $svcnum, $method ) = (shift, shift, shift);
+ my $jobnum = ''; #don't actually care
+ $self->communigate_pro_queue_dep( \$jobnum, $svcnum, $method, @_);
+}
+
+sub communigate_pro_queue_dep {
+ my( $self, $jobnumref, $svcnum, $method ) = splice(@_,0,4);
+
my %kludge_methods = (
'CreateAccount' => 'CreateAccount',
'UpdateAccountSettings' => 'UpdateAccountSettings',
@@ -246,11 +415,12 @@ sub communigate_pro_queue {
my $sub = exists($kludge_methods{$method})
? $kludge_methods{$method}
: 'communigate_pro_command';
+
my $queue = new FS::queue {
'svcnum' => $svcnum,
'job' => "FS::part_export::communigate_pro::$sub",
};
- $queue->insert(
+ my $error = $queue->insert(
$self->machine,
$self->option('port'),
$self->option('login'),
@@ -258,7 +428,9 @@ sub communigate_pro_queue {
$method,
@_,
);
+ $$jobnumref = $queue->jobnum unless $error;
+ return $error;
}
sub communigate_pro_runcommand {
@@ -302,7 +474,7 @@ sub CreateAccount {
my $accountType = delete $args{'accountType'};
my $externalFlag = delete $args{'externalFlag'};
$args{'AccessModes'} = [ split(' ', $args{'AccessModes'}) ];
- my @args = ( accountName => $accountName,
+ my @args = ( accountName => $accountName,
accountType => $accountType,
settings => \%args,
);
@@ -314,8 +486,7 @@ sub CreateAccount {
}
sub UpdateAccountSettings {
- my( $machine, $port, $login, $password, $method, %args ) = @_;
- my $accountName = delete $args{'accountName'};
+ my( $machine, $port, $login, $password, $method, $accountName, %args ) = @_;
$args{'AccessModes'} = [ split(' ', $args{'AccessModes'}) ];
my @args = ( $accountName, \%args );
communigate_pro_command( $machine, $port, $login, $password, $method, @args );