6 use FS::Record qw( dbh qsearch qsearchs );
13 @ISA = qw( FS::Record );
17 FS::agent - Object methods for agent records
23 $record = new FS::agent \%hash;
24 $record = new FS::agent { 'column' => 'value' };
26 $error = $record->insert;
28 $error = $new_record->replace($old_record);
30 $error = $record->delete;
32 $error = $record->check;
34 $agent_type = $record->agent_type;
36 $hashref = $record->pkgpart_hashref;
37 #may purchase $pkgpart if $hashref->{$pkgpart};
41 An FS::agent object represents an agent. Every customer has an agent. Agents
42 can be used to track things like resellers or salespeople. FS::agent inherits
43 from FS::Record. The following fields are currently supported:
47 =item agentnum - primary key (assigned automatically for new agents)
49 =item agent - Text name of this agent
51 =item typenum - Agent type. See L<FS::agent_type>
53 =item prog - For future use.
55 =item freq - For future use.
57 =item disabled - Disabled flag, empty or 'Y'
59 =item username - Username for the Agent interface
61 =item _password - Password for the Agent interface
71 Creates a new agent. To add the agent to the database, see L<"insert">.
75 sub table { 'agent'; }
79 Adds this agent to the database. If there is an error, returns the error,
80 otherwise returns false.
84 Deletes this agent from the database. Only agents with no customers can be
85 deleted. If there is an error, returns the error, otherwise returns false.
92 return "Can't delete an agent with customers!"
93 if qsearch( 'cust_main', { 'agentnum' => $self->agentnum } );
98 =item replace OLD_RECORD
100 Replaces OLD_RECORD with this one in the database. If there is an error,
101 returns the error, otherwise returns false.
105 Checks all fields to make sure this is a valid agent. If there is an error,
106 returns the error, otherwise returns false. Called by the insert and replace
115 $self->ut_numbern('agentnum')
116 || $self->ut_text('agent')
117 || $self->ut_number('typenum')
118 || $self->ut_numbern('freq')
119 || $self->ut_textn('prog')
121 return $error if $error;
123 if ( $self->dbdef_table->column('disabled') ) {
124 $error = $self->ut_enum('disabled', [ '', 'Y' ] );
125 return $error if $error;
128 if ( $self->dbdef_table->column('username') ) {
129 $error = $self->ut_alphan('username');
130 return $error if $error;
131 if ( length($self->username) ) {
132 my $conflict = qsearchs('agent', { 'username' => $self->username } );
133 return 'duplicate agent username (with '. $conflict->agent. ')'
134 if $conflict && $conflict->agentnum != $self->agentnum;
135 $error = $self->ut_text('password'); # ut_text... arbitrary choice
137 $self->_password('');
141 return "Unknown typenum!"
142 unless $self->agent_type;
149 Returns the FS::agent_type object (see L<FS::agent_type>) for this agent.
155 qsearchs( 'agent_type', { 'typenum' => $self->typenum } );
158 =item pkgpart_hashref
160 Returns a hash reference. The keys of the hash are pkgparts. The value is
161 true if this agent may purchase the specified package definition. See
166 sub pkgpart_hashref {
168 $self->agent_type->pkgpart_hashref;
171 =item ticketing_queue
173 Returns the queue name corresponding with the id from the I<ticketing_queueid>
174 field, or the empty string.
178 sub ticketing_queue {
180 FS::TicketSystem->queue($self->ticketing_queueid);
183 =item num_prospect_cust_main
185 Returns the number of prospects (customers with no packages ever ordered) for
190 sub num_prospect_cust_main {
191 shift->num_sql(FS::cust_main->prospect_sql);
195 my( $self, $sql ) = @_;
196 my $statement = "SELECT COUNT(*) FROM cust_main WHERE agentnum = ? AND $sql";
197 my $sth = dbh->prepare($statement) or die dbh->errstr." preparing $statement";
198 $sth->execute($self->agentnum) or die $sth->errstr. " executing $statement";
199 $sth->fetchrow_arrayref->[0];
202 =item prospect_cust_main
204 Returns the prospects (customers with no packages ever ordered) for this agent,
205 as cust_main objects.
209 sub prospect_cust_main {
210 shift->cust_main_sql(FS::cust_main->prospect_sql);
214 my( $self, $sql ) = @_;
215 qsearch( 'cust_main',
216 { 'agentnum' => $self->agentnum },
222 =item num_active_cust_main
224 Returns the number of active customers for this agent.
228 sub num_active_cust_main {
229 shift->num_sql(FS::cust_main->active_sql);
232 =item active_cust_main
234 Returns the active customers for this agent, as cust_main objects.
238 sub active_cust_main {
239 shift->cust_main_sql(FS::cust_main->active_sql);
242 =item num_susp_cust_main
244 Returns the number of suspended customers for this agent.
248 sub num_susp_cust_main {
249 shift->num_sql(FS::cust_main->susp_sql);
254 Returns the suspended customers for this agent, as cust_main objects.
259 shift->cust_main_sql(FS::cust_main->susp_sql);
262 =item num_cancel_cust_main
264 Returns the number of cancelled customer for this agent.
268 sub num_cancel_cust_main {
269 shift->num_sql(FS::cust_main->cancel_sql);
272 =item cancel_cust_main
274 Returns the cancelled customers for this agent, as cust_main objects.
278 sub cancel_cust_main {
279 shift->cust_main_sql(FS::cust_main->cancel_sql);
282 =item num_active_cust_pkg
284 Returns the number of active customer packages for this agent.
288 sub num_active_cust_pkg {
289 shift->num_pkg_sql(FS::cust_pkg->active_sql);
293 my( $self, $sql ) = @_;
295 "SELECT COUNT(*) FROM cust_pkg LEFT JOIN cust_main USING ( custnum )".
296 " WHERE agentnum = ? AND $sql";
297 my $sth = dbh->prepare($statement) or die dbh->errstr." preparing $statement";
298 $sth->execute($self->agentnum) or die $sth->errstr. "executing $statement";
299 $sth->fetchrow_arrayref->[0];
302 =item num_susp_cust_pkg
304 Returns the number of suspended customer packages for this agent.
308 sub num_susp_cust_pkg {
309 shift->num_pkg_sql(FS::cust_pkg->susp_sql);
312 =item num_cancel_cust_pkg
314 Returns the number of cancelled customer packages for this agent.
318 sub num_cancel_cust_pkg {
319 shift->num_pkg_sql(FS::cust_pkg->cancel_sql);
322 =item generate_reg_codes NUM PKGPART_ARRAYREF
324 Generates the specified number of registration codes, allowing purchase of the
325 specified package definitions. Returns an array reference of the newly
326 generated codes, or a scalar error message.
330 #false laziness w/prepay_credit::generate
331 sub generate_reg_codes {
332 my( $self, $num, $pkgparts ) = @_;
334 my @codeset = ( 'A'..'Z' );
336 local $SIG{HUP} = 'IGNORE';
337 local $SIG{INT} = 'IGNORE';
338 local $SIG{QUIT} = 'IGNORE';
339 local $SIG{TERM} = 'IGNORE';
340 local $SIG{TSTP} = 'IGNORE';
341 local $SIG{PIPE} = 'IGNORE';
343 my $oldAutoCommit = $FS::UID::AutoCommit;
344 local $FS::UID::AutoCommit = 0;
349 my $reg_code = new FS::reg_code {
350 'agentnum' => $self->agentnum,
351 'code' => join('', map($codeset[int(rand $#codeset)], (0..7) ) ),
353 my $error = $reg_code->insert($pkgparts);
355 $dbh->rollback if $oldAutoCommit;
358 push @codes, $reg_code->code;
361 $dbh->commit or die $dbh->errstr if $oldAutoCommit;
369 Returns the number of unused registration codes for this agent.
375 my $sth = dbh->prepare(
376 "SELECT COUNT(*) FROM reg_code WHERE agentnum = ?"
377 ) or die dbh->errstr;
378 $sth->execute($self->agentnum) or die $sth->errstr;
379 $sth->fetchrow_arrayref->[0];
382 =item num_prepay_credit
384 Returns the number of unused prepaid cards for this agent.
388 sub num_prepay_credit {
390 my $sth = dbh->prepare(
391 "SELECT COUNT(*) FROM prepay_credit WHERE agentnum = ?"
392 ) or die dbh->errstr;
393 $sth->execute($self->agentnum) or die $sth->errstr;
394 $sth->fetchrow_arrayref->[0];
404 L<FS::Record>, L<FS::agent_type>, L<FS::cust_main>, L<FS::part_pkg>,
405 schema.html from the base documentation.