Want to show your appreciation and help with hosting costs? Support us on Patreon!
Submitted by Admin on March 31, 2014

Section 1 (PHP)

<?php
/**
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 */

/**
 * The main API class, used to map the api interfaces
 * 
 * @author Nikki
 * 
 */
class SteamWebAPI {
	
	public $key;
	
	private $interfaces;
	
	public function __construct($key) {
		$this->key = $key;
	}
	
	public function __get($property) {
		if(!empty($this->interfaces->$property)) {
			return $this->interfaces->$property;
		}
	}
	
	public function LoadSupportedAPIList($file = false, $update = false) {
		if(!$update && !empty($file) && file_exists($file) && filesize($file) > 0) {
			$this->interfaces = new stdClass;
			$apis = json_decode(file_get_contents($file));
			foreach($apis as $obj) {
				$this->interfaces->{$obj->name} = new SteamWebAPIInterface($this, $obj->name, $obj->methods);
			}
		} else {
			$json = $this->request('ISteamWebAPIUtil', 'GetSupportedAPIList', 1, $this->make_request());
			
			// Map it into a format we can easily use
			$apis = new stdClass;
			$this->interfaces = new stdClass;
			foreach($json->apilist->interfaces as $obj) {
				$methods = new stdClass;
				foreach($obj->methods as $method) {
					$methods->{$method->name} = $method;
				}
				
				$this->interfaces->{$obj->name} = new SteamWebAPIInterface($this, $obj->name, $methods);
				
				$apis->{$obj->name} = array('name' => $obj->name, 'methods' => $methods);
			}
			if(!empty($file)) {
				file_put_contents($file, json_encode($apis));
			}
		}
	}
	
	private function make_request(array $info = array()) {
		return array_merge($info, array('key' => $this->key));
	}
	
	public function request($api, $method, $version, array $info) {
		$version = 'v' . str_pad("$version", 4, "0", STR_PAD_LEFT);
		$url = sprintf("http://api.steampowered.com/%s/%s/%s/?%s", $api, $method, $version, http_build_query($info));
		if(function_exists('curl_init')) {
			$ch = curl_init();
			curl_setopt($ch, CURLOPT_URL, $url);
			curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
			curl_setopt($ch, CURLOPT_HEADER, false);
			
			$res = curl_exec($ch);
			
			curl_close($ch);
		} else if(function_exists('file_get_contents') && ini_get('allow_url_fopen')) {
			$res = file_get_contents($url);
		} else {
			trigger_error('Unable to find a valid HTTP request method, please enable allow_url_fopen or install cURL.', E_SEVERE);
			return false;
		}
		
		if($res[0] != '{') {
			trigger_error('Invalid response from Steam API', E_SEVERE);
			return false;
		}
		
		return json_decode($res);
	}
}

/**
 * The API Interface class used to actually call the methods
 * 
 * @author Nikki
 *
 */
class SteamWebAPIInterface {
	private $name;
	private $api;
	private $methods;
	
	public function __construct($api, $name, $methods) {
		$this->api = $api;
		$this->name = $name;
		$this->methods = $methods;
	}
	
	public function __call($name, $arguments) {
		if(!empty($this->methods->$name)) {
			$api = $this->methods->$name;
			
			$args = array();
			
			$parameters = $api->parameters;
			if($api->parameters[0]->name == 'key') {
				array_shift($parameters);
				
				if (empty($api->requires_key)) {
					$api->requires_key = true;
				}
			}
			$paramCount = count($parameters);
			
			if(!empty($arguments)) {
				if(is_array($arguments[0])) {
					$arguments = $arguments[0];
					$argCount = count($parameters);
					// Verify arguments exist
					for($i = 0; $i < $paramCount; $i++) {
						$arg = $parameters[$i];
						if(!isset($arguments[$arg->name])) {
							return false;
						}
						$args[$arg->name] = $arguments[$arg->name];
					}
				} else {
					// Verify arguments and order
					// TODO actual ordering somehow? For now it assumes that the api list order doesn't change.
					for($i = 0; $i < $paramCount; $i++) {
						$arg = $parameters[$i];
						if(!isset($arguments[$i]) && empty($arg->optional)) {
							return;
						}
						$args[$arg->name] = $arguments[$i];
					}
				}
			}
			
			if ($api->requires_key) {
				$args['key'] = $this->api->key;
			}
			
			return $this->api->request($this->name, $name, $api->version, $args);
		}
	}
}