/*
 * suck_group.c
 * 
 * $Id: suck_group.c,v 1.2 2002/06/06 14:21:06 conrads Exp $
 * 
 * Sucks a range of new articles (if any) from a remote news server and feeds
 * them to a local server
 */

#include <sys/types.h>
#include <time.h>
#include <unistd.h>

#include "msuck.h"

extern CONNECTION remote, local;
extern FILE *sucklog;
extern char xoverpath[], resultspath[];
static char fetchpath[PATH_MAX + 1];

/*
 * suck all new articles in group whose newsrc index is 'i'
 * 
 * returns number fetched, or -1 on error
 */
int
suck_group(SERVER * server, int i)
{
	ARTNUM last_art, remote_active_lo, remote_active_hi, lo, hi;
	int newarticles, numtofetch, numfetched, numkilled;
	char group[MAXGROUP + 1];

	ptrtostr(server->newsrc->mmapped[i].group, group);

	snprintf(fetchpath, PATH_MAX, "/tmp/fetch.%s", group);

	if (file_exists(fetchpath))
		return 0;
	if (touch(fetchpath) == -1)
		return 0;

	if ((last_art = ptrtonum(server->newsrc->mmapped[i].lastart)) == 0)
	{
		fprintf(stderr, "suck_group(): couldn't get local newsrc info for %s\n",
			group);
		unlink(fetchpath);
		return -1;
	}

	/*
	 * get active info for group on remote server (connection to remote
	 * server left open if successful)
	 */
	if (connect_to_server(server->hostname, (CONNECTION *)&remote) <= 0)
	{
		unlink(fetchpath);
		return -1;
	}

	if (!get_active_info(remote, group, &remote_active_lo, &remote_active_hi))
	{
		fprintf(stderr, "suck_group(): couldn't get remote active info for %s\n", group);
		close_server(remote);
		unlink(fetchpath);
		return -1;
	}

	/*
	 * calculate range to try to suck
	 */
	lo = last_art + 1;

	if (lo < remote_active_lo)
		lo = remote_active_lo;

	hi = remote_active_hi;

	newarticles = (hi - lo) + 1;

	if (newarticles <= 0)
	{
		quit_server(remote);
		unlink(fetchpath);
		return 0;
	}

	/*
	 * note: do_xover expects an open connection on entry, which it
	 * closes on exit
	 */
	if (do_xover(group, lo, hi) <= 0)
	{
		unlink(fetchpath);
		return -1;
	}

	/* filter out unwanted articles */

	fprintf(sucklog, "Filtering %d articles in %s\n", newarticles, group);

	if ((numtofetch = filter_group(group)) < 0)
	{
		fprintf(stderr, "suck_group(): filter_group(%s) returned error\n", group);
		unlink(resultspath);
		unlink(fetchpath);
		return -1;
	}

	/* filtering succeeded, results are now in another file */
	unlink(xoverpath);

	/* print the results of the filtering */

	numkilled = newarticles - numtofetch;

	if (numkilled > 0)
	{
		fprintf(sucklog, "Killed %d articles in %s\n", numkilled, group);
	}

	/* now do the actual fetching */
	if (numtofetch > 0)
	{
		fprintf(sucklog, "Fetching %d articles in %s\n", numtofetch, group);

		if (connect_to_server(server->hostname, &remote) <= 0)
		{
			unlink(fetchpath);
			return -1;
		}

		if ((numfetched = getarticles(group, numtofetch)) < 0)
		{
			fprintf(stderr, "suck_group(): getarticles(%s, %d) returned error\n",
				group, numtofetch);
			close_server(remote);
		}
		else
		{
			fprintf(sucklog, "Got %d articles in %s\n", numfetched, group);
			quit_server(remote);
		}
	}
	else
	{
		fprintf(sucklog, "Nothing to get in %s\n", group);
		numfetched = 0;
	}

	update_newsrc(server->newsrc->mmapped[i].lastart, hi);
	unlink(resultspath);
	unlink(fetchpath);
	return numfetched;
}


syntax highlighted by Code2HTML, v. 0.9.1