<?php
/*******************************************************************************
 * Copyright (c) 2010, 2017 Eclipse Foundation and others.
 *
 * This program and the accompanying materials are made available under the
 * terms of the Eclipse Public License v. 2.0 which is available at
 * http://www.eclipse.org/legal/epl-2.0.
 *
 * SPDX-License-Identifier: EPL-2.0
 ********************************************************************************/

require_once (dirname(__FILE__) . "/Forge.class.inc");
require_once (dirname(__FILE__) . "/License.class.inc");
require_once (dirname(__FILE__) . "/database.inc");
require_once (dirname(__FILE__) . "/debug.php");
require_once (dirname(__FILE__) . "/common.php");

define('PROJECT_LIVELINESS_NEVER_ACTIVE', 0);
define('PROJECT_LIVELINESS_ACTIVE', 1);
define('PROJECT_LIVELINESS_STALE', 2);
define('PROJECT_LIVELINESS_INACTIVE', 2);
define('PROJECT_LIVELINESS_DEAD', 4);

define('PROJECT_REPO_ALL_GIT', 1);
define('PROJECT_REPO_SOME_GIT', 2);
define('PROJECT_REPO_NO_GIT', 3);
define('PROJECT_REPO_NONE', 4);

define('TRADEMARK_REGISTERED', 1);
define('TRADEMARK_UNREGISTERED', 2);
define('TRADEMARK_FILED', 3);

define('TRADEMARK_ALL', TRADEMARK_REGISTERED | TRADEMARK_UNREGISTERED);

/**
 * Get a project from the PMI instead of the foundation database.
 * Going directly to the PMI is no longer necessary now that the
 * implementation has been cleaned up. Now, we can just load the
 * project; if information is required from the PMI, it will be
 * loaded from there.
 *
 * @deprecated use Project::getProject()
 * @param string $id
 *        a project id of the form 'technology.egit'
 * @return PMIProject
 */
function get_project_from_pmi($id) {
  return Project::getProject($id);
}

/**
 * Answers an array containing all top-level projects.
 * Only
 * active projects are included.
 *
 * @deprecated Use Project::getTopLevelProjects()
 * @return Project[]
 */
function getTopLevelProjects() {
  PMIProject::preload();
  return Project::getTopLevelProjects();
}

/**
 * This function returns an instance of Project representing the project
 * with the provided $id.
 * Note that this function preserves object
 * identity: if called twice with the same value, it will return the
 * exact same object.
 *
 * @deprecated Use Project::getProject($id)
 * @return Project
 */
function getProject($id) {
  return Project::getProject($id);
}

/**
 *
 * @deprecated Use Project::getProject($id)
 * @return Project
 */
function get_project($id) {
  return Project::getProject($id);
}

/**
 * This function returns all the active projects.
 *
 * @deprecated Use Project::getActiveProjects()
 * @return Project[]
 */
function getActiveProjects() {
  return Project::getActiveProjects();
}

/**
 * Instances of the subclasses of Project represent a single Eclipse Foundation
 * Project.
 * Projects may be in any of the forges supported by the Eclipse
 * Foundation.
 *
 * This class has two subclasses. The ProductProxy class is basically the
 * entry-point; when you ask for a project, you first get one of these. These
 * instances are pretty cheap to make and can answer a lot of questions. When
 * requests are made that require more information, that information is
 * gathered from the PMI and results in the creation of a PMIProduct instance
 * (loading from the PMI is pretty expensive, so we try to avoid it when we
 * can).
 *
 * The entry points are all static methods on this class. Instances should
 * never be created using the constructors.
 *
 * Note that instances are cached as they are loaded; subsequent queries
 * will always return the cached instance.
 */
abstract class Project {
  static $config;
  static $projects = array();

  /**
   * Initialize the class by loading the configuration from
   * projects.ini. The projects.ini file includes information about
   * how projects have moved (e.g. 'technology.ecf' became 'rt.ecf'),
   * information about Top Level Project specific brands, etc.
   */
  static function init() {
  	self::$config = parse_ini_file(dirname(__FILE__) . '/projects.ini');
  }

  /**
   * Get all projects regardless of whether or not they are active
   * or archived. The Foundation database is used to get this information.
   * This implementation takes project moves that occurred in the day
   * when we duplicated information (e.g. there are records in the
   * database for 'technology.ecf' and 'rt.ecf') into consideration.
   * A project that has been moved will only be represented once in
   * this query.
   *
   * This move information is represented in the projects.ini file.
   *
   * Other pseudo projects are also skipped by this query.
   *
   * @return ProjectProxy[]|mixed[]
   */
  public static function getAll() {
  	// Skip all pseudo projects.
  	$skip = array("'root'", "'foundation-internal'", "'galileo'");

  	// Skip all projects that were duplicated in a move operation.
  	// TODO Consider encapsulating this access of the static field.
  	foreach(self::$config['move'] as $from => $to) {
  		$skip[] = "'{$from}'";
  	}
  	$skip = implode(',', $skip);
    return self::getProjects(array(
      "IsComponent = 0",
      "(p.ProjectID not in ($skip))",
      "(p.ParentProjectID not in ('foundation-internal'))"
    ));
  }

  public static function getProject($id) {
    if (!isValidProjectId($id))
      return null;
    $projects = self::getProjects(array(
      "(p.ProjectId = '$id')"
    ));
    if ($projects)
      return $projects[$id];
    return null;
  }

  public static function getAllProjects($ids) {
    $all = array();
    foreach($ids as $id) {
    	if (isValidProjectId($id)) {
    		$all[] = "'{$id}'";
    	}
    }
    $all = implode(',', $all);
    return self::getProjects(array(
    	"(p.ProjectId in ($all))"
    ));
  }

  private static function getAlternateForgeIds() {
    $forges = array();
    foreach (Forge::getForges() as $forge) {
      if (!$forge->isEclipseForge())
        $forges[] = "'{$forge->getId()}'";
    }
    return implode(',', $forges);
  }

  public static function getTopLevelProjects() {
    $forges = self::getAlternateForgeIds();
    $where = array(
		"p.IsActive",
      	"(p.ProjectID not in ('root', 'foundation-internal', 'galileo'))",
		"(p.ParentProjectID not in ('foundation-internal'))");
    if ($forges)
		$where[] = "((p.ParentProjectID = 'root' and p.ProjectId not in ($forges)) or p.ParentProjectID in ($forges))";
    else
    	$where[] = "p.ParentProjectID = 'root'";

    return self::getProjects($where);
  }

  public static function getActiveProjects() {
    $forges = self::getAlternateForgeIds();
    $where = array(
    		"p.IsActive",
    		"(p.ProjectID not in ('root', 'foundation-internal', 'galileo'))",
    		"(p.ParentProjectID not in ('foundation-internal'))");
    if ($forges)
    	$where[] = "(p.ProjectId not in ($forges))";

    return self::getProjects($where);
  }

  public static function getProjectsForCommitter($id) {
    $forges = self::getAlternateForgeIds();
    $where = array(
    		"(p.ProjectID in (SELECT ProjectID FROM PeopleProjects where PersonId='$id' and Relation='CM' and InactiveDate is null))",
    		"p.IsActive"
    );
    if ($forges)
    	$where[] = "(p.ProjectId not in ($forges))";

    return self::getProjects($where);
  }

  /**
   * This function answers an array containing all those projects that
   * use the license with the provided id.
   *
   * @param string $id the license id as expressed in the Foundation DB (e.g. 'EPL-2.0')
   * @return Project[]
   */
  public static function getProjectsWithLicense($id) {
   return self::getProjects(array(
     "p.ProjectId in (select ProjectId from ProjectLicenses where LicenseId='{$id}')",
     "p.IsActive"
   ));
  }

  public static function getSubprojects($id) {
    return self::getProjects(array(
      "(p.ParentProjectId = '$id')",
      "p.IsActive"
    ));
  }

  public static function visit($callable, $pre = null, $post = null) {
    if ($pre) call_user_func($pre, null);
    foreach (self::getTopLevelProjects() as $project) {
      $project->visitHierarchy($callable, $pre, $post, 0);
    }
    if ($post) call_user_func($post, null);
  }

  private static function getProjects($conditions) {
    $where = join(' and ', $conditions);

    $sql = "
            SELECT distinct
                p.ProjectId as id, p.Name as name, p.ParentProjectID as parent, p.ProjectPhase as phase,
                p.UrlDownload,
                group_concat(distinct l.LicenseId) as licenses,
                min(pp.ActiveDate) as provisioned_date,
                group_concat(distinct cm.PersonId) as committer_ids,
                group_concat(distinct pl.PersonId) as lead_ids
            FROM Projects as p
                left join ProjectLicenses as l on p.ProjectId=l.ProjectId
                left join PeopleProjects as pp on p.ProjectId=pp.ProjectId
                left join PeopleProjects as cm on p.ProjectId=cm.ProjectId and cm.Relation='CM' and cm.InactiveDate is null
                left join PeopleProjects as pl on p.ProjectId=pl.ProjectId and pl.Relation='PL' and pl.InactiveDate is null
            where
                $where
            group by p.ProjectId";

    $projects = array();
    query('foundation', $sql, null, function ($row) use (&$projects) {
      $id = $row['id'];
      if (isset(Project::$projects[$id])) {
        $projects[$id] = Project::$projects[$id];
      }
      else {
        $project = new ProjectProxy($id, $row);
        Project::$projects[$id] = $project;
        $projects[$id] = $project;
      }
    });

    // The configuration defines projects that should be removed
    // from query results. Remove those projects.
    // TODO Consider encapsulating this access of the static field.
    foreach(self::$config['remove'] as $remove) {
    	unset($projects[$remove]);
    }

    return $projects;
  }

  private function __construct() {
  }

  /**
   * Answer the raw name of the receiver. This is
   * the name as it appears in the data. We almost
   * never want to use this directly. Instead, use
   * the nick name or formal name.
   *
   * @see Project::getNickName()
   * @see Project::getFormalName()
   */
  public abstract function getName();

  public abstract function getId();

  public abstract function getParentId();

  public abstract function getProjectPhase();

  public abstract function getProxy();

  /**
   * The short id is the last segment in the fully-qualified
   * id. e.g. the short id of 'technology.egit' is 'egit'.
   *
   * @return string
   */
  public function getShortId() {
   preg_match("/([^\.]+)$/", $this->getId(), $matches);
   return $matches[1];
  }

  public function getLocalId() {
    return $this->getForge()->getLocalProjectId($this->getId());
  }

  public function getShortName() {
    return $this->getName();
  }

  public function getChildren() {
    return self::getSubprojects($this->getId());
  }

  public function getParent() {
    return self::getProject($this->getParentId());
  }

  public function isInIncubationPhase() {
    return in_array($this->getProjectPhase(), array(
      'Incubation',
      'Incubation.nc'
    ));
  }

  /**
   * Components are an old concept.
   * Nothing is a component anymore.
   *
   * @return boolean Always false
   */
  public function isComponent() {
    return false;
  }

  public function isArchived() {
    return $this->getProjectPhase() == 'Archived';
  }

  public function isInIncubationConformingPhase() {
    return $this->getProjectPhase() == 'Incubation';
  }

  public function isInIncubationNonConformingPhase() {
    return false;
  }

  public function getUrl() {
    $id = $this->getLocalId();
    $base = $this->getForge()->getUrl();
    return "{$base}/projects/{$id}";
  }

  /**
   * This function answers the URL to use to get more data
   * about the project in JSON format, including releases, etc.
   */
  public function getDataUrl() {
	if (!$forge = Forge::getForgeForProjectId($this->getId())) {
		return null;
	}
	$base = $forge->getUrl();
	$local = $forge->getLocalProjectId($this->getId());
	return "{$base}/json/project/$local";
  }

  public function getTopLevelProject() {
    if ($this->isTopLevel())
      return $this;
    if (!$parent = $this->getParent())
      return $this;
    return $parent->getTopLevelProject();
  }

  public function isTopLevel() {
    if (!$forge = $this->getForge())
      return true;
    if ($forge->isEclipseForge())
      return $this->getParentId() == 'root';
    return $this->getParentId() == $forge->getId();
  }

  public function getForge() {
    return Forge::getForgeForProjectId($this->getId());
  }

  public function visitHierarchy($function, $pre = null, $post = null, $level) {
    call_user_func($function, $this, $level);
    if ($pre) call_user_func($pre, $this);
    foreach ($this->getChildren() as $child) {
      $child->visitHierarchy($function, $pre, $post, $level + 1);
    }
    if ($post) call_user_func($post, $this);
  }

  /**
   * This method answers the formal name of the project. If the
   * project's name does not include either 'Eclipse', or the
   * brand name associated with its Top Level Project, then the
   * brand name is prepended to the project name.
   *
   * Remove anything that's between parentheses. We actually
   * look for a space followed by an open parenthesis, because
   * some projects (e.g. "Eclipse e(fx)clipse") include them
   * in their proper name (and "Eclipse eclipse" just looks weird).
   *
   * e.g.
   * <li>"EGit" becomes "Eclipse EGit"</li>
   * <li>"e(fx)clipse" becomes "Eclipse e(fx)clipse"</li>
   * <li>"Eclipse Communication Framework (ECF)" becomes "Eclipse Communication Framework"</li>
   * <li>"PolarSys Capella" becomes "PolarSys Capella"</li>
   * <li>"Capella" becomes "PolarSys Capella"</li>
   *
   * @see Project::getNickName()
   *
   * @return string
   */
  public function getFormalName() {
  	$brand = $this->getBrandName();

    $name = trim(preg_replace('/ \([^\)]*\)/', ' ', $this->getName()));
    if (!preg_match("/(?:$brand|Eclipse)/", $name)) {
    	return "$brand $name";
    }
    return $name;
  }

  /**
   * Sort out the project's brand. If the project name starts with one of our brands,
   * as defined in the projects.ini file, then that is the project's brand.
   * The project's brand might also be determined by the top-level project
   * (a top-level project may have a brand associated with it; in this case,
   * all projects that fall under that top-level project use that brand.
   *
   * @return string
   */
  public function getBrandName() {
  	foreach(@self::$config['brands'] as $brand) {
  		if (preg_match("/^{$brand}/", $this->getName())) return $brand;
  	}

  	if ($brand = @self::$config['tlp'][$this->getTopLevelProject()->getId()])
  		return $brand;
  	return 'Eclipse';
  }

  /**
   * This method answers the nickname for the project.
   * The name of the project as listed in the foundation database is the best
   * source of this information. This is difficult to guess as sometimes the
   * forge name is part of the nick name and sometimes it's not. Values are
   * stored in the foundation database as the nickname with optional acronym in
   * parentheses. This method strips anything in parentheses from the returned
   * value.
   *
   * We actually look for a space followed by an open parenthesis, because
   * some projects (e.g. "Eclipse e(fx)clipse") include them
   * in their proper name (and "Eclipse eclipse" just looks weird).
   *
   * @see Project::getFormalName()
   *
   * @return string
   */
  public function getNickName() {
    // We get the proxy and ask it for the name.
    return trim(preg_replace('/ \([^\)]*\)/', ' ', $this->getProxy()->getName()));
  }

  /**
   *
   * @deprecated
   *
   * @return NULL
   */
  public function getNoteworthyUrl() {
    return null;
  }

  /**
   *
   * @deprecated
   *
   */
  public function getNewsgroups() {
    return array();
  }

  /**
   *
   * @deprecated
   *
   * @return null|Proposal
   */
  public function getProposal() {
    // FIXME Implement. Or don't.
    return null;
  }

  public function getLiveliness() {
    if (!$this->getCommitActivity())
      return PROJECT_LIVELINESS_NEVER_ACTIVE;
    if ($this->hasRecentCommitActivity(3))
      return PROJECT_LIVELINESS_ACTIVE;
    if ($this->hasRecentCommitActivity(6))
      return PROJECT_LIVELINESS_STALE;
    if ($this->hasRecentCommitActivity(12))
      return PROJECT_LIVELINESS_INACTIVE;

    return PROJECT_LIVELINESS_DEAD;
  }

  /**
   * Answers whether or not the receiver has recent commit activity.
   *
   * @param int $months
   *        (Optional) how many months in the past to check.
   * @return boolean
   */
  public function hasRecentCommitActivity($months = 6) {
    $activity = $this->getCommitActivity();
    $date = strtotime('now');
    while ($months) {
      if (@$activity[date('Ym', $date)])
        return true;
      $date = strtotime("-1 month", $date);
      $months--;
    }
    return false;
  }

  /**
   * Returns the commit activity for the receiver in the form of an
   * array mapping period to commit count.
   *
   * e.g.,
   *
   * array('201001' => 52, '201002' => 33, ...)
   *
   * Note that this information is cached. The first time this method
   * is called (on any instance), the cache is created.
   *
   * @returns [] array mapping period to commit count.
   */
  public function getCommitActivity() {
    if (isset($this->_commitActivity))
      return $this->_commitActivity;

    $id = $this->getId();
    $sql = "select period, count from ProjectCommitActivity where project='$id'";

    $this->_commitActivity = array();
    query('dashboard', $sql, array(), function ($row) {
      $this->_commitActivity[$row['period']] = $row['count'];
    });
    return $this->_commitActivity;
  }
}

/**
 * This class implements a lightweight stand-in to represent a
 * project.
 * The basic idea is that it is far less expensive to
 * query the Foundation Database for information about projects
 * than it is to query the PMI. However, the PMI has a lot more
 * information. Instances of this class provide as much information
 * as they can, but then defer to the PMI when more information is
 * required.
 *
 * @see Project
 */
class ProjectProxy extends Project {
  private $id;
  private $data;
  private $project;

  public function __construct($id, $data) {
    $this->id = $id;
    $this->data = $data;
  }

  public function __toString() {
    return "Project ({$this->getId()})";
  }

  public function getId() {
    return $this->id;
  }

  public function getParentId() {
    return $this->data['parent'];
  }

  public function getProxy() {
    return $this;
  }

  public function getName() {
   return preg_replace ( '/ Root$/', '', $this->data ['name'] );
  }

  public function getProjectPhase() {
    return $this->data['phase'];
  }

  /**
   * We don't directly track the date of project provisioning.
   * Rather, we leverage a feature of the provisioning process by
   * which the provisioning process is triggered when the first
   * committer is ready to be assigned to the project (this is
   * figured into the query that we pull from the Foundation DB).
   *
   * This function returns our best guess at the provisioning date
   * in UNIX date format, or null if no such date can be determined.
   *
   * @see Project::getProjects
   * @return NULL|number
   */
  public function getProvisionedDate() {
    if (!isset($this->data['provisioned_date'])) return null;
    return strtotime($this->data['provisioned_date']);
  }

  public function hasProjectLeads() {
    return !empty($this->data['lead_ids']);
  }

  public function hasCommitters() {
  	return !empty($this->data['committer_ids']);
  }

  public function getSpecificationWorkingGroupName() {
  	$apiData = $this->getAPIData();
  	return @$apiData[0]['spec_project_working_group']['name'];
  }

  public function isSpecificationProject() {
  	$apiData = $this->getAPIData();
  	return !empty($apiData[0]['spec_project_working_group']);
  }

  /**
   * Get the data related to this project from the Eclipse API.
   *
   * @return array|mixed
   */
  private function getAPIData() {
  	if (@$this->apiData === NULL) {
	  	$url = 'https://projects.eclipse.org/api/projects/' . preg_replace('/\./','_',$this->getId());
	  	$ch = curl_init();
	  	curl_setopt($ch, CURLOPT_URL, $url);
	  	curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
	  	$this->apiData = json_decode(curl_exec($ch), true);
	  	curl_close($ch);
	  	if (!$this->apiData) $this->apiData = array();
  	}
  	return $this->apiData;
  }

  /**
   *
   * @deprecated
   * @return License[]
   */
  public function getLicenses() {
   return License::getLicensesForProject($this->getId());
  }

  /**
   * Answer a statement (suitable for use in a file header)
   * that describes the licenses of the project.
   *
   * @deprecated Use License::getLicensesStatement
   * @return string
   */
  public function getLicensesStatement() {
   return License::getLicensesStatement($this->getLicenses());
  }

  /**
   * @deprecated Use License::getSPDXLicenseExpression
   * @return string
   */
  public function getSPDXLicenseExpression() {
   return License::getSPDXExpression($this->getLicenses());
  }

  /**
   * @deprecated Use License::getDefaultFileHeader
   * @return string
   */
  public function getDefaultFileHeader() {
   return License::getDefaultFileHeader($this->getLicenses());
  }

  /**
   * @deprecated Use License::getAlternativeFileHeader
   * @return string
   */
  public function getAlternativeFileHeader() {
   return License::getAlternativeFileHeader($this->getLicenses());
  }

  /**
   * Answers an array containing the trademarks that are known
   * to be associated with the project.
   *
   * @return string[]
   */
  function getTrademarks($type = TRADEMARK_ALL, $includeForge = false) {
   $trademarks = array();
   if ($type & TRADEMARK_UNREGISTERED) {
     $this->trademarksDo($type, function($value) use (&$trademarks) {
       $trademarks[] = $value;
     });
   }
   return $trademarks;
  }

  /**
   * Iterate over the trademarks that are known to be associated
   * with the project.
   *
   * The primary source of information is the name of the project
   * as it is represented in the Foundation Database. If the project
   * name includes something in parentheses, then this implementation
   * assumes that something is a nickname or alternative name. Or, if there
   * are two names separated by <space><dash><space> they are treated
   * as separate names.
   *
   * Further, the configuration (projects.ini) defines zero or more "brands"
   * (e.g. 'LocationTech' or 'PolarSys') that are connected to a particular
   * Top Level Project. When the brand applies to a project and is not
   * already represented in the name, the brand is prepended to the name.
   * 'Eclipse' is the default brand.
   *
   * The number of trademarks that may be associated with a project
   * is open-ended. The callable may be executed any number (or zero)
   * times.
   *
   * e.g.
   * <li>'LocationTech GeoGig' maps to 'LocationTech GeoGig'</li>
   * <li>'GeoGig' maps to 'LocationTech GeoGig' and 'GeoGig'</li>
   * <li>'Eclipse EMF' maps so 'EMF'</li>
   * <li>'EMF' maps to 'Eclipse EMF' and 'EMF'</li>
   *
   * @see Project::init()
   * @see Project::normalizedTrademarksDo()
   *
   * @param string $type TRADEMARK_REGISTERED | TRADEMARK_UNREGISTERED
   * @param callable $function Function that takes a single argument.
   */
  function trademarksDo($type, $function) {
   if (preg_match('/(?:releng|website)$/', $this->getId())) return;
   $name = $this->getName();

   // TODO Deal with different trademark types.

    if (preg_match('/^([^\\(]+)\s\\(([^\\)]+)\\)/', $name, $matches)) {
     $this->normalizedTrademarksDo($function,$matches[1]);
     $this->normalizedTrademarksDo($function,$matches[2]);
    } elseif (preg_match('/^([^-]*)\s\\-\s([^-]*)$/', $name, $matches)) {
     $this->normalizedTrademarksDo($function,$matches[1]);
     $this->normalizedTrademarksDo($function,$matches[2]);
    } else {
     $this->normalizedTrademarksDo($function,$name);
    }

    if ($extra = @$this::$config['trademarks'][$this->getId()]) {
    	call_user_func($function, $extra);
    }
  }

  /**
   * Execute the function with each of the normalized trademarks extracted
   * from a term. The normalized trademarks for a particular
   * term are the term itself, along with the term prefixed
   * (if it does not already include) with the corresponding brand.
   *
   * e.g.
   * <li>"EclipseLink" normalizes as "EclipseLink"
   * <li>"EGit" normalizes as "EGit" and "Eclipse EGit"
   * <li>"Capella" normalizes as "Capella" and "PolarSys Capella"
   *
   * This script uses the branding information provided in
   * the project.ini file to map the Top Level project of the
   * receiver to a brand (default is "Eclipse").
   *
   * @see Project::getBrandName()
   * @see Project::getFormalName()
   * @see ProjectProxy::trademarksDo()
   *
   * @param callable $function
   * @param string $term The project name (e.g. 'EGit')
   */
  private function normalizedTrademarksDo($function, $term) {
  	$term = trim($term);
  	if (empty($term)) return;
  	$term = preg_replace('/\s?\\[[^\\]]*\\]/','', $term);

	// First check to see if the name uses one of the general brands;
	// if so, then that's the project name. When one of the general
	// brands does not apply, check for use of the TLP-specific
	// brand; when that brand is not present, both the name from the
	// database and that name prepended with the TLP-specific brand
	// are considered trademarks.
  	$brands = @self::$config['brands'];
  	$brands=implode('|', $brands);
	if (preg_match("/^(?:{$brands})/", $term)) {
  		call_user_func($function, "{$brand} {$term}");
	} else {
		$brand = $this->getBrandName();
		if (!preg_match("/(?:{$brand})/", $term)) {
			call_user_func($function, "{$brand} {$term}");
		}
		call_user_func($function, $term);
	}
  	return;
  }

  public function getDownloadUri() {
    if (!$url = $this->data['UrlDownload'])
      return null;
      // TODO We should probably ask the forge for the downloadUrl
    $forge = $this->getForge()->getId();
    if (!preg_match("/^https?:\/\/download.{$forge}.org\/(.*)$/", $url, $matches))
      return null;
    return $matches[1];
  }

  public function __call($name, $arguments) {
    if (!$project = $this->getPMIProject())
      return null;
    return call_user_func_array(array(
      $project,
      $name
    ), $arguments);
  }

  private function getPMIProject() {
    if ($this->project === null) {
      $project = PMIProject::getProject($this->getId());
      $this->project = $project ? $project : FALSE;
    }
    return $this->project;
  }

}

/**
 * Representation of an Eclipse Foundation project with information
 * obtained from a PMI instance.
 * Instances of this class should rarely
 * be made directly; use the static methods on Project to obtain
 * instances.
 *
 * @see Project
 */
class PMIProject extends Project {
  private $data;
  private $forge;
  private static $cache = array();

  /**
   * Obtain an representation of a project from a PMI instance.
   *
   * This method should not generally be used directly. Instead,
   * use the static methods on Project to obtain a reference to a project
   * and that reference will make this call if it is required.
   *
   * @param string $id
   * @return NULL|PMIProject
   */
  public static function getProject($id) {
    if (isset(self::$cache[$id]))
      return self::$cache[$id];

    if (!$forge = Forge::getForgeForProjectId($id))
      return null;
    $base = $forge->getUrl();
    $local = $forge->getLocalProjectId($id);
    $url = "{$base}/json/project/$local";

    $ch = curl_init();
    curl_setopt($ch, CURLOPT_URL, $url);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    $json = curl_exec($ch);
    curl_close($ch);

    if (!$json)
      return null;

    if (!$all = json_decode($json, true))
      return null;
    if (!$data = $all['projects'][$local])
      return null;

    return new PMIProject($data, $forge);
  }

  /**
   * @deprecated
   */
  public static function preload() {
  }

  private function __construct($data, $forge) {
    $this->data = $data;
    $this->forge = $forge;
  }

  /**
   * Answer the project's id as it appears in the Foundation Database.
   * The PMI data contains the local id. If the project comes from an
   * alternate forge, then the forge id is prepended to the local value.
   *
   * @return string
   */
  public function getId() {
    return $this->getForge()->getFoundationDBId($this->getLocalId());
  }

  public function getLocalId() {
    return $this->data['id'][0]['value'];
  }

  public function getForge() {
    return $this->forge;
  }

  public function getProxy() {
    // TODO Consider caching this value
    return Project::getProject($this->getId());
  }

  public function getName() {
    // TODO Get the name (when it's available)
    return $this->data['title'];
  }

  public function getDescription() {
    if (!$field = @$this->data['description'][0])
      return null;
    if (!empty($field['summary']))
      return $field['summary'];
    if (!empty($field['safe_value']))
     return $field['safe_value'];
    $value = $field['value'];
    $paragraphs = explode("\n", $value);
    return $paragraphs[0];
  }

  public function getScope() {
    if (!$field = @$this->data['scope'][0])
      return null;
    if (!empty($field['summary']))
      return $field['summary'];
    return @$field['safe_value'];
  }

  /**
   * Answer the project phase.
   * In the PMI, this is represented in
   * the "state" field. Two out of three values match what we do
   * in the Foundation Database. For the third, "Incubating", we
   * change it "Incubation" for consistency.
   *
   * @return string
   */
  public function getProjectPhase() {
    $state = $this->data['state'][0]['value'];
    if ($state == 'Incubating')
      return 'Incubation';
    return $state;
  }

  public function getDevListUrl() {
    return $this->data['dev_list']['url'];
  }

  public function getPlanUrl() {
    return @$this->data['plan_url'][0]['url'];
  }

  public function getWikiUrl() {
    return @$this->data['wiki_url'][0]['url'];
  }

  public function getDocumentationUrl() {
    return @$this->data['documentation_url'][0]['url'];
  }

  public function getDownloadsUrl() {
    return @$this->data['download_url'][0]['url'];
  }

  public function getGettingStartedUrl() {
    return @$this->data['gettingstarted_url'][0]['url'];
  }

  /**
   * Answer an array containing information about the source
   * repositories registered for the project.
   *
   * @return SourceRepository[]
   */
  public function getSourceRepositories() {
    $repositories = array();
    foreach ($this->data['source_repo'] as $repo) {
      $repositories[] = new SourceRepository($this, $repo);
    }
    return $repositories;
  }

  public function getBugzillaProduct() {
    foreach ($this->data['bugzilla'] as $record) {
      if (strlen($record['product']) > 0)
        return $record['product'];
    }
    return null;
  }

  public function getBugzillaComponents() {
    $components = array();
    foreach ($this->data['bugzilla'] as $record) {
      if (strlen($record['component']) > 0)
        $components[] = $record['component'];
    }
    return $components;
  }

  public function getMailingLists() {
    // FIXME Implement this
    return array();
  }

  /**
   * Answer the project's parent's id as it appears in the Foundation Database.
   * The PMI data contains the local id. If the project comes from an
   * alternate forge, then the forge id is prepended to the local value.
   *
   * @return string
   */
  public function getParentId() {
    return $this->getForge()->getFoundationDBId(@$this->data['parent_project'][0]['id']);
  }

  /**
   *
   * @deprecated
   *
   * @return string
   */
  function getProjectUrl() {
    return $this->getUrl();
  }

  /**
   * Answer an array of information regarding project releases.
   *
   * @return PMIRelease[]
   */
  function getReleases() {
    $releases = array();
    if (isset($this->data['releases'])) {
      foreach ($this->data['releases'] as $data) {
        $releases[] = new PMIRelease($this, $data);
      }
    }
    return $releases;
  }

  public function getReviews() {
    // FIXME Consider implementing this.
    return array();
  }

  /**
   * Answers the release that falls after a particular time.
   * If a date is not provided in the parameter, the current
   * date and time is assumed.
   *
   * @param int $time
   *        UNIX date.
   */
  public function getNextRelease($since = null) {
    if (!$since)
      $since = time();
    $releases = $this->getReleases();
    usort($releases, function ($a, $b) {
      return $a->getDate() == $b->getDate() ? 0 : ($a->getDate() < $b->getDate() ? -1 : 1);
    });

    foreach ($releases as $release) {
      if ($release->getDate() > $since)
        return $release;
    }

    return null;
  }

}
class PMIRelease {
  private $project;
  private $data;

  function __construct($project, $data) {
    $this->project = $project;
    $this->data = $data;
  }

  public function getTitle() {
    return $this->data['title'];
  }

  public function getName() {
    return $this->getTitle();
  }

  /**
   * Answers the UNIX date of the release.
   *
   * @return int
   */
  public function getDate() {
    foreach ($this->data['date'] as $data) {
      return strtotime($data['value']);
    }
    return null;
  }

  /**
   * Answers the URL for the release record.
   * If the information
   * is provided with the PMI data, then return that value. Otherwise,
   * make a very good guess at the value using the project URL and
   * the standard pattern for naming releases.
   *
   * Most of the time, the guess will be correct. But since the PMI
   * uses pathauto and there some cases where the project team e.g.
   * creates two releases with the same name, there is some risk that
   * the URL will be invalid. This risk is relatively low, however,
   * as we we usually (always?) have a URL from the PMI.
   *
   * @return string
   */
  public function getUrl() {
    if ($url = $this->data['url'])
      return $url;
    $url = $this->project->getUrl();
    $title = $this->getTitle();
    return "$url/releases/$title";
  }

  public function getNoteworthyUrl() {
    return @$this->data['noteworthy'][0]['url'];
  }
}

class SourceRepository {
  private $project;
  private $data;

  public function __construct($project, $data) {
    $this->project = $project;
    $this->data = $data;
  }

  /**
   * Answer the project that owns the reciever.
   *
   * @return Project
   */
  public function getProject() {
    return $this->project;
  }

  public function getName() {
    return $this->data['name'];
  }

  public function getPath() {
    return $this->data['path'];
  }

  public function providesCommitActivity() {
    return true;
  }

  public function isReal() {
    // TODO test to see if the receiver represents a real repository.
    return true;
  }

  /**
   * Get the repository-technology specific URL for the repository.
   * e.g. git://git.eclipse.org/gitroot/jgit/jgit.git
   */
  public function getUrl() {
    return $this->data['url'];
  }

  public function getType() {
    return $this->data['type'];
  }

  /**
   * Return an HTTP link for the receiver.
   * i.e. something that is suitable
   * for a browser
   */
  public function getLink() {
    return $this->getUrl();
  }

}

/**
 * Sort the array of projects by the given key.
 * Valid keys
 * are 'name', or 'top' (top level project).
 *
 * @param Project[] $projects
 * @param string $key
 */
function sortProjects(&$projects, $key = 'name') {
  if (!in_array($key, array(
    'name',
    'top'
  )))
    $key = 'name';

  return usort($projects, "_sortProjects_$key");
}

/**
 * Sort by Project name
 *
 * @internal
 *
 * @param Project $a
 * @param Project $b
 * @return number
 */
function _sortProjects_name($a, $b) {
  return strcasecmp($a->getName(), $b->getName());
}

/**
 * Sort project by Top Level Project.
 *
 * @internal
 *
 * @param Project $a
 * @param Project $b
 * @return number
 */
function _sortProjects_top($a, $b) {
  return strcasecmp($a->getTopLevelProject()->getName(), $b->getTopLevelProject()->getName());
}

// Initialize the class
Project::init();
?>