Business Networks

Scope

In this example we will be using PHP to build and populate a SocialOS
network. In the process, we will:

  • Create a network
  • Create user records
  • Use the membership workflow to manage users joining our network
  • Post messages and comments to the network
  • View the resulting message stream via the API
  • View the same message stream via the pre-build stream widget

To keep this example both general and simple, we won't be using an
application framework such as Laravel here, just a simple client library
to manage our API access.

The sample application prints out a list of operations as it runs so
that you can follow the process.

Application Code

<?php
include 'easyapi.php';

admin('GET', 'test');

# This resets your SocialOS sandbox environment; use with care.
admin('POST', 'debug/reset');

# Here we create a number of users.
# If we don't specify a password, a random password is generated by SocialoS.
# We record it in this example so that we can make API calls as the various users.

print("Creating users.\n");

$jill = admin('POST', 'user',
    array(
        'name' => 'jill_j',
        'domain' => 'example.com',
        'address' => '[email protected]',
        'email' => '[email protected]',
        'bio' => array(
            'screen_name' => 'Jill Jalapeno',
            'avatar' => 'https://s3.amazonaws.com/uifaces/faces/twitter/pixeliris/128.jpg'
        )
    )
);
$jill_auth = $jill->address . ':' . $jill->password;

$mike = admin('POST', 'user',
    array(
        'name' => 'mike_m',
        'domain' => 'example.com',
        'address' => '[email protected]',
        'email' => '[email protected]',
        'bio' => array(
            'screen_name' => 'Mike Mustard',
            'avatar' => 'https =>//s3.amazonaws.com/uifaces/faces/twitter/danbenoni/128.jpg'
        )
    )
);
$mike_auth = $mike->address . ':' . $mike->password;


$jeff = admin('POST', 'user',
    array(
        'name' => 'jeff_j',
        'domain' => 'example.com',
        'address' => '[email protected]',
        'email' => '[email protected]',
        'bio' => array('screen_name' => 'Jeff Juniper',
            'avatar' => 'https =>//s3.amazonaws.com/uifaces/faces/twitter/tomaslau/128.jpg'
        )
    )
);
$jeff_auth = $jeff->address . ':' . $jeff->password;

$mona = admin('POST', 'user',
    array(
        'name' => 'mona_m',
        'domain' => 'example.com',
        'address' => '[email protected]',
        'email' => '[email protected]',
        'bio' => array(
            'screen_name' => 'Mona Macademia',
            'avatar' => 'https =>//s3.amazonaws.com/uifaces/faces/twitter/ladylexy/128.jpg'
        )
    )
);
$mona_auth = $mona->address . ':' . $mona->password;


$lisa = admin('POST', 'user',
    array(
        'name' => 'lisa_l',
        'domain' => 'example.com',
        'address' => '[email protected]',
        'email' => '[email protected]',
        'bio' => array(
            'screen_name' => 'Lisa Lettuce',
            'avatar' => 'https =>//s3.amazonaws.com/uifaces/faces/twitter/allisongrayce/128.jpg'
        )
    )
);
$lisa_auth = $lisa->address . ':' . $lisa->password;


$todd = admin('POST', 'user',
    array(
        'name' => 'todd_t',
        'domain' => 'example.com',
        'address' => '[email protected]',
        'email' => '[email protected]',
        'bio' => array(
            'screen_name' => 'Todd Tabasco',
            'avatar' => 'https =>//s3.amazonaws.com/uifaces/faces/twitter/arminophen/128.jpg'
        )
    )
);

$todd_auth = $todd->address . ':' . $todd->password;

print("Creating persona.\n");
$persona = api('POST', 'persona',
    array(
        'name' => 'mike_m',
        'domain' => 'example.com',
        'address' => '[email protected]',
        'email' => '[email protected]',
        'social' => array(
            array('site' => 'twitter', 'id' => '@mikemustard'),
            array('site' => 'facebook', 'id' => 'Mean Mike Mustard'),
            array('site' => 'reddit', 'id' => '/u/mikemustard')
        ),
    ),
    $mike_auth
);

print("Creating widget user.\n");
$widget = admin('POST', 'user',
    array(
        'name' => 'widget',
        'domain' => 'example.com',
        'address' => '[email protected]',
        'password' => $widget_pwd
    )
);

$m = array();

print("Creating messages.\n");
$msg = api('POST', 'message', array('text' => 'Jill, have you seen the layout for the new add campaign?'), $mike_auth);
$m[] = $msg;

$msg = api('POST', 'message/' . $m[0]->id . '/reply',
    array(
        'text' => 'Yes, I thought it was very striking. We may just want to change the font choices to they fit better with our logo.'
    ),
    $jill_auth
);
$m[] = $msg;
$msg = api('GET', 'message/' . $m[1]->id, null, $mike_auth);


# Now we will create a moderated network, and have our users join it, using the membership workflow.
print("Creating network.\n");
$network = api('POST', 'network',
    array(
        'name' => 'Example',
        'path' => 'example',
        'membership' => 'moderated'
    ),
    $mike_auth
);

$networks = api('GET', 'network/name/Example', null, $mike_auth);

# NOTE => Through SocialOS R209b4, the owner of a network must manually join the network after creation.
# Fixed since SocialOS R209b5.
api('POST', 'network/join/' . $network->id, $mike_auth);

# Here each of the users applys to join the network and is approved by the owner
api('POST', 'network/apply/' . $network->id, null, $jill_auth);
api('POST', 'network/approve/' . $network->id . '/user/' . $jill->id, null, $mike_auth);
api('POST', 'network/apply/' . $network->id, null, $jeff_auth);
api('POST', 'network/approve/' . $network->id . '/user/' . $jeff->id, null, $mike_auth);
api('POST', 'network/apply/' . $network->id, null, $lisa_auth);
api('POST', 'network/approve/' . $network->id . '/user/' . $lisa->id, null, $mike_auth);
api('POST', 'network/apply/' . $network->id, null, $mona_auth);
api('POST', 'network/approve/' . $network->id . '/user/' . $mona->id, null, $mike_auth);
api('POST', 'network/apply/' . $network->id, null, $todd_auth);
api('POST', 'network/approve/' . $network->id . '/user/' . $todd->id, null, $mike_auth);

$netids = array($network->id);

print("Creating network messages\n");
$msg = api('POST', 'message',
    array(
        'networks' => $netids,
        'text' => 'The sample copy for the Winter 2015 ad campaign is circulating now. I suggest we switch to Helvetica Neue for the display copy.'
    ),
    $jill_auth
);

sleep(1);  # So that our messages are in order
$msg = api('POST', 'message',
    array(
        'networks' => $netids,
        'text' => 'Lisa, could you get on that today? I\'ve given you access to the fonts database.'
    ),
    $mona_auth
);

sleep(1);
$msg = api('POST', 'message',
    array(
        'networks' => $netids,
        'text' => 'On it right now. I\'ll need to adjust the spacing and alignment, so I\'ll send you a draft for approval as soon as it\'s ready.'
    ),
    $lisa_auth
);

sleep(1);
$msg = api('POST', 'message',
    array(
        'networks' => $netids,
        'text' => 'Done! Mona, the draft pages are up on the internal website.'
    ),
    $lisa_auth
);

sleep(1);
$msg = api('POST', 'message',
    array(
        'networks' => $netids,
        'text' => 'That looks great. Todd, I\'m ready to sign off on these. Any thoughts? '
    ),
    $mona_auth
);

sleep(1);
$msg = api('POST', 'message',
    array(
        'networks' => $netids,
        "text" => "Looks good to me. Legal already approved the copy, and the deadline for print is Tuesday, so let\"s go ahead."
    ),
    $todd_auth
);

$messages = api('GET', 'message/network/' . $network->id, null, $jill_auth);
var_dump($messages);

Client Library Code (PHP)

<?php
$api_url = 'https://your-api-url:port/';
$admin_url = 'https://your-admin-url:port/';
$admin_auth = 'admin@mydomain:password';
$widget_pwd = 'widget_password';


function rawapi($method, $url, $data = null, $auth = null, $headers = null)
{
    $ch = curl_init($url);
    curl_setopt($ch, CURLOPT_CUSTOMREQUEST, $method);
    curl_setopt($ch, CURLOPT_USERPWD, $auth);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

    if ($data)
        curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data));

    if (!$headers)
        $headers = array();

    if ($method == 'GET' or !$data)
        $headers[] = 'Content-Length: 0';
    else
        $headers[] = 'Content-Type: application/json';

    curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);

    return json_decode(curl_exec($ch));
}

function admin($method, $url, $data = null, $headers = null)
{
    global $admin_url, $admin_auth;

    return rawapi($method, $admin_url . $url, $data, $admin_auth, $headers);
}


function api($method, $url, $data = null, $auth = null, $headers = null)
{
    global $api_url;

    return rawapi($method, $api_url . $url, $data, $auth, $headers);
}

Client Library Code (Python)

This is a simple library for Python that is call-for-call compatible
with the sample PHP client library above. It uses the Requests library
and (for convenience) the third-party library Bunch.

import json

import requests
# noinspection PyUnresolvedReferences
from bunch import bunchify, Bunch

api_url = None
admin_url = None
admin_auth = (None, None)


class APIError(Exception):
    pass


# Utility functions
def setup(**kw):
    global api_url, admin_url, admin_auth

    if 'api_url' in kw:
        api_url = kw['api_url']
    if 'admin_url' in kw:
        admin_url = kw['admin_url']
    if 'admin_auth' in kw:
        admin_auth = kw['admin_auth']


def admin(method, query, data=None, headers=None, auth=None, as_user=None):
    if not auth:
        auth = admin_auth
    if not headers:
        headers = {}
    if method == 'GET' and not data:
        headers['Content-Length'] = 0
    elif data:
        headers['Content-Type'] = 'application/json'
    if as_user:
        headers['As-User'] = as_user

    r = requests.request(method.upper(), '%s/%s' % (admin_url, query), data=json.dumps(data), headers=headers,
                         auth=auth)

    if r.status_code >= 400:
        raise APIError(r.text)
    else:
        return bunchify(r.json())


def api(method, query, data=None, headers=None, auth=None):
    if not headers:
        headers = {}
    if method == 'GET' and not data:
        headers['Content-Length'] = 0
    elif data:
        headers['Content-Type'] = 'application/json'

    r = requests.request(method.upper(), '%s/%s' % (api_url, query), data=json.dumps(data), headers=headers,
                         auth=auth)

    if r.status_code >= 400:
        raise APIError(r.text)
    else:
        return bunchify(r.json())


def show(data):
    print(json.dumps(data, sort_keys=True))


def say(text):
    print('\n' + text + '\n')

API Examples

Python

jill = admin('POST', 'user',
             data={
                 'name': 'jill_j',
                 'domain': 'example.com',
                 'address': '[email protected]',
                 'email': '[email protected]',
                 'bio': {
                     'screen_name': 'Jill Jalapeno',
                     'avatar': 'https://s3.amazonaws.com/uifaces/faces/twitter/pixeliris/128.jpg'
                 }
             }
             )

PHP

$jill = admin('POST', 'user',
    array(
        'name' => 'jill_j',
        'domain' => 'example.com',
        'address' => '[email protected]',
        'email' => '[email protected]',
        'bio' => array(
            'screen_name' => 'Jill Jalapeno',
            'avatar' => 'https://s3.amazonaws.com/uifaces/faces/twitter/pixeliris/128.jpg'
        )

    )
);