Q:

How is this for an API structure

I have just written an API framework which I am hoping to implement into one of my large sites very soon. However, before I do so, I want to be sure that the script is well written and there are no obvious mistakes that I have missed.
As with most projects, the key here is automation and speed... I have tried to automate as much as possible whilst also keeping expensive code to a minimum.
These are a few sample requests that one could fire at this API:
// Return the logged in users details
http://api.example.net/user/

// Return the registered companies for the logged in user
http://api.example.net/user/companies/

Where user is the $object on both and 'default' is the $request on the first and 'companies' is the $request on the second...
The data is then retrieved based on the $request on the $object... Make sense? :-) I hope so, here is my code:
<?php

    // +------------------------------------------------------------------------+
    // | api.php                                                                |
    // +------------------------------------------------------------------------+
    // | Copyright (c) Example Ltd 2012. All rights reserved.                   |
    // | Version       1.0                                                      |
    // | Last modified 14/05/2013                                               |
    // | Email         dev@example.net                                          |
    // | Web           https://api.example.net                                  |
    // +------------------------------------------------------------------------+

    /*
     * Example API
     *
     * @version   1.0
     * @author    Ben Carey <ben.carey@example.net>
     * @copyright Example Ltd
     *
    */

    // Guidelines for creating and adding a working method
    // 1. All functions must have $parameters=array() as their only parameter
    // 2. All must return some sort of data
    // 3. Set the $example->json_constants if you need to specify anything about the JSON output
    // 4. Any errors place into $example->error (string) and return
    // Once the method has been created, you can proceed to adding it to the API
    // 1. Work out what address you want e.g. api.example.net/user/companies
    //      -> This example will translate to the domain api.example.net/api.php?object=user&request=companies
    // 2. If the object has a corresponding class and the class does not already exist in the defined list then add it
    // 3. If the object does not have a corresponding class, it is an alias so add it (if not already there), to the alias array
    // and map it to the correct class
    // 4. Now you need to map the request to the method. If there is no request set (e.g. /user instead of /user/companies) then the request
    // is treated as 'default'. You can then specify in the $api_methods array $object -> $request -> $method

    // Define the allowed domains,
    // this will prevent other sites from being able to
    // access the API via AJAX
    $allowed_domains = array('http://beta.example.net','https://beta.example.net');

    // Test if the domain is allowed to connect
    if(isset($_SERVER['HTTP_ORIGIN'])&&in_array($_SERVER['HTTP_ORIGIN'],$allowed_domains)){
        // Allow access to the current domain
        header('Access-Control-Allow-Origin: '.$_SERVER['HTTP_ORIGIN']);
    }

    // Include the site configuration
    include('C:\Inetpub\vhosts\example.net\subdomains\beta\httpdocs\_snippets\_system\config.php');

    // Define the Example Classes
    // All of these paths link to the class initiation file,
    // in other words, by including them it will include all
    // necessary files and create an instance of the class
    $classes = array(
        'authorized'    => $_PATHS['EXAMPLE'].'\_snippets\_classes\class.authorized.php',
        'documents'     => $_PATHS['EXAMPLE'].'\_snippets\_classes\class.documents.php',
        'reports'       => $_PATHS['EXAMPLE'].'\_snippets\_classes\class.reports.php',
        'settings'      => $_PATHS['EXAMPLE'].'\_snippets\_classes\class.settings.php',
    );

    // Create a map of aliases to classes
    // This will allow objects that do not have a matching class but
    // but do have a corresponding method in another class
    // specified here
    $class_aliases = array(
        'user'      => 'authorized',
        'company'   => 'authorized'
    );

    // Gather the relevant methods for the supplied
    // request method
    switch($_SERVER['REQUEST_METHOD']){
        case 'GET':
            // Create an array that maps the objects to the 
            // relevant request and method within the class
            $api_methods = array(
                'authorized'    => array(
                    'default'               => 'get_authorized'
                ),
                'documents'     => array(
                    'sessions'              => 'get_active_sessions'
                ),
                'masterfiles'   => array(
                    'items'                 => 'get_master_file_items',
                    'properties'            => 'get_master_file_properties',
                    'reference'             => 'get_master_file_reference'
                ),
                'user'          => array(
                    'companies'             => 'get_registered_companies_for_user'
                )
            );
            // Set the parameters to be passed to the corresponding
            // method, this is set depending on the page request method
            $parameters = $_GET;
        break;
        case 'POST':
            // Create an array that maps the objects to the 
            // relevant request and method within the class
            $api_methods = array(
                'settings'  => array(
                    'user' => 'update_user'
                )
            );
            // Set the parameters to be passed to the corresponding
            // method, this is set depending on the page request method
            $parameters = $_POST;
        break;
    }

    // The object and request are always supplied via GET
    $object = strtolower($_GET['object']);
    $request = strtolower($_GET['request']);

    // Set the class to include based on the object supplied
    if(isset($classes[$object])){
        $class = $classes[$object]; 
    }elseif(isset($class_aliases[$object])){
        $class = $classes[$class_aliases[$object]];
    }else{
        $data = array('error' => 'Specified object does not exist');    
    }   

    // Set the method to execute based on the request supplied
    if(!empty($request)&&isset($api_methods[$object][$request])){
        $method = $api_methods[$object][$request];
    }elseif(isset($api_methods[$object]['default'])){
        $method = $api_methods[$object]['default'];
    }else{
        $data = array('error' => 'Specified request does not exist');
    }

    // Only proceed if there are no errors
    if(empty($data)){

        // If the request is via AJAX then prevent all redirects
        if(isset($_SERVER['HTTP_X_REQUESTED_WITH'])&&strtolower($_SERVER['HTTP_X_REQUESTED_WITH'])=='xmlhttprequest'){
            $prevent_redirect = true;
        }

        // Include the relevant class
        include($class);

        // Remove the request and method values from the parameters
        unset($parameters['object'],$parameters['request']);

        // Execute the relevant method
        $data = call_user_func(array($example,$method));

        // If there was an error then replace the data variable
        $data = !empty($example->error) ? array('error' => $example->error) : $data;
    }

    echo json_encode($data,$example->json_constants);

?>

A:

Ignoring your code for a second, here's some feedback on the design of your API.
It may be better to simply include the user's companies in the response for the /user endpoint. This would make your code more complex, but API consumers' lives easier.
Obviously removing the /user/companies endpoint eliminates the ability to request ONLY company data for a specific user. If you feel it's important to be able to request this information on its own, then here's two options.

Allow partial responses via GET parameters (i.e. GET /user?fields=companies) or something similar with JSON in the request body.
Decouple the companies endpoint from the /user endpoint and create a top-level /companies endpoint. Provide a way to query by user ID, and you could get the same data as /user/company

As a final note, if you ever plan on allowing queries for information on users other than the current user, you may want to use a "me" placeholder in the endpoint like so: /user/me. If you were to use a modern routing library like Slim, you can easily support queries for the current user and arbitrary users simply by parsing everything after the slash (/) like so:
$app->get('/user/:user_id', function ($user_id) {
    if ('me' == $user_id) {
        // Get the current user
    } else {
        // Get user with ID $user_id
    }
    ...
});

