mirror of
https://we.phorge.it/source/phorge.git
synced 2024-11-10 00:42:41 +01:00
Make Aphlict client somewhat more approachable
Summary: Provide a reasonable JS API for the Aphlict client. Provide an example behavior to invoke it. Test Plan: Ran "aphlict_server.js" with: $ sudo node aphlict_server.js Loaded /aphlict/. Opened console. Got "hello" from the server every second. Got reasonable errors with the server not present ("Security exception", but this is because it can't connect to port 843 to access the policy server). Reviewers: ddfisher, keebuhm, allenjohnashton, btrahan Reviewed By: btrahan CC: aran, epriestley Maniphest Tasks: T944 Differential Revision: https://secure.phabricator.com/D1800
This commit is contained in:
parent
140927926d
commit
f8431bbfee
13 changed files with 310 additions and 23 deletions
|
@ -321,6 +321,17 @@ celerity_register_resource_map(array(
|
|||
),
|
||||
'disk' => '/rsrc/css/application/herald/herald-test.css',
|
||||
),
|
||||
'javelin-aphlict' =>
|
||||
array(
|
||||
'uri' => '/res/50cae715/rsrc/js/application/aphlict/Aphlict.js',
|
||||
'type' => 'js',
|
||||
'requires' =>
|
||||
array(
|
||||
0 => 'javelin-install',
|
||||
1 => 'javelin-util',
|
||||
),
|
||||
'disk' => '/rsrc/js/application/aphlict/Aphlict.js',
|
||||
),
|
||||
'javelin-behavior' =>
|
||||
array(
|
||||
'uri' => '/res/0017f840/rsrc/js/javelin/lib/behavior.js',
|
||||
|
@ -331,6 +342,19 @@ celerity_register_resource_map(array(
|
|||
),
|
||||
'disk' => '/rsrc/js/javelin/lib/behavior.js',
|
||||
),
|
||||
'javelin-behavior-aphlict-listen' =>
|
||||
array(
|
||||
'uri' => '/res/6388e057/rsrc/js/application/aphlict/behavior-aphlict-listen.js',
|
||||
'type' => 'js',
|
||||
'requires' =>
|
||||
array(
|
||||
0 => 'javelin-behavior',
|
||||
1 => 'javelin-aphlict',
|
||||
2 => 'javelin-util',
|
||||
3 => 'javelin-stratcom',
|
||||
),
|
||||
'disk' => '/rsrc/js/application/aphlict/behavior-aphlict-listen.js',
|
||||
),
|
||||
'javelin-behavior-aphront-basic-tokenizer' =>
|
||||
array(
|
||||
'uri' => '/res/9be30797/rsrc/js/application/core/behavior-tokenizer.js',
|
||||
|
@ -1658,17 +1682,6 @@ celerity_register_resource_map(array(
|
|||
),
|
||||
'disk' => '/rsrc/css/application/slowvote/slowvote.css',
|
||||
),
|
||||
0 =>
|
||||
array(
|
||||
'uri' => '/res/b6096fdd/rsrc/js/javelin/lib/__tests__/URI.js',
|
||||
'type' => 'js',
|
||||
'requires' =>
|
||||
array(
|
||||
0 => 'javelin-uri',
|
||||
1 => 'javelin-php-serializer',
|
||||
),
|
||||
'disk' => '/rsrc/js/javelin/lib/__tests__/URI.js',
|
||||
),
|
||||
'phabricator-standard-page-view' =>
|
||||
array(
|
||||
'uri' => '/res/7e09bbfc/rsrc/css/application/base/standard-page-view.css',
|
||||
|
@ -1892,6 +1905,17 @@ celerity_register_resource_map(array(
|
|||
),
|
||||
'disk' => '/rsrc/css/core/syntax.css',
|
||||
),
|
||||
0 =>
|
||||
array(
|
||||
'uri' => '/res/b6096fdd/rsrc/js/javelin/lib/__tests__/URI.js',
|
||||
'type' => 'js',
|
||||
'requires' =>
|
||||
array(
|
||||
0 => 'javelin-uri',
|
||||
1 => 'javelin-php-serializer',
|
||||
),
|
||||
'disk' => '/rsrc/js/javelin/lib/__tests__/URI.js',
|
||||
),
|
||||
), array(
|
||||
'packages' =>
|
||||
array(
|
||||
|
|
|
@ -445,6 +445,7 @@ phutil_register_library_map(array(
|
|||
'MetaMTAConstants' => 'applications/metamta/constants/base',
|
||||
'MetaMTANotificationType' => 'applications/metamta/constants/notificationtype',
|
||||
'Phabricator404Controller' => 'applications/base/controller/404',
|
||||
'PhabricatorAphlictTestPageController' => 'applications/notifications/controller/test',
|
||||
'PhabricatorAuditActionConstants' => 'applications/audit/constants/action',
|
||||
'PhabricatorAuditAddCommentController' => 'applications/audit/controller/addcomment',
|
||||
'PhabricatorAuditComment' => 'applications/audit/storage/auditcomment',
|
||||
|
@ -621,6 +622,7 @@ phutil_register_library_map(array(
|
|||
'PhabricatorMetaMTAViewController' => 'applications/metamta/controller/view',
|
||||
'PhabricatorMetaMTAWorker' => 'applications/metamta/worker',
|
||||
'PhabricatorMySQLFileStorageEngine' => 'applications/files/engine/mysql',
|
||||
'PhabricatorNotificationsController' => 'applications/notifications/controller/base',
|
||||
'PhabricatorOAuthClientAuthorization' => 'applications/oauthserver/storage/clientauthorization',
|
||||
'PhabricatorOAuthClientAuthorizationBaseController' => 'applications/oauthserver/controller/clientauthorization/base',
|
||||
'PhabricatorOAuthClientAuthorizationDeleteController' => 'applications/oauthserver/controller/clientauthorization/delete',
|
||||
|
@ -1247,6 +1249,7 @@ phutil_register_library_map(array(
|
|||
'ManiphestView' => 'AphrontView',
|
||||
'MetaMTANotificationType' => 'MetaMTAConstants',
|
||||
'Phabricator404Controller' => 'PhabricatorController',
|
||||
'PhabricatorAphlictTestPageController' => 'PhabricatorNotificationsController',
|
||||
'PhabricatorAuditAddCommentController' => 'PhabricatorAuditController',
|
||||
'PhabricatorAuditComment' => 'PhabricatorAuditDAO',
|
||||
'PhabricatorAuditCommitListView' => 'AphrontView',
|
||||
|
@ -1390,6 +1393,7 @@ phutil_register_library_map(array(
|
|||
'PhabricatorMetaMTAViewController' => 'PhabricatorMetaMTAController',
|
||||
'PhabricatorMetaMTAWorker' => 'PhabricatorWorker',
|
||||
'PhabricatorMySQLFileStorageEngine' => 'PhabricatorFileStorageEngine',
|
||||
'PhabricatorNotificationsController' => 'PhabricatorController',
|
||||
'PhabricatorOAuthClientAuthorization' => 'PhabricatorOAuthServerDAO',
|
||||
'PhabricatorOAuthClientAuthorizationBaseController' => 'PhabricatorOAuthServerController',
|
||||
'PhabricatorOAuthClientAuthorizationDeleteController' => 'PhabricatorOAuthClientAuthorizationBaseController',
|
||||
|
|
|
@ -423,6 +423,8 @@ class AphrontDefaultApplicationConfiguration
|
|||
'channel/(?P<channel>[^/]+)/' =>
|
||||
'PhabricatorChatLogChannelLogController',
|
||||
),
|
||||
|
||||
'/aphlict/' => 'PhabricatorAphlictTestPageController',
|
||||
);
|
||||
}
|
||||
|
||||
|
|
|
@ -0,0 +1,37 @@
|
|||
<?php
|
||||
|
||||
/*
|
||||
* Copyright 2012 Facebook, Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
abstract class PhabricatorNotificationsController
|
||||
extends PhabricatorController {
|
||||
|
||||
public function buildStandardPageResponse($view, array $data) {
|
||||
|
||||
$page = $this->buildStandardPageView();
|
||||
|
||||
$page->setApplicationName('Notifications');
|
||||
$page->setBaseURI('/notifications/');
|
||||
$page->setTitle(idx($data, 'title'));
|
||||
$page->setGlyph('!');
|
||||
$page->appendChild($view);
|
||||
|
||||
$response = new AphrontWebpageResponse();
|
||||
return $response->setContent($page->render());
|
||||
|
||||
}
|
||||
|
||||
}
|
15
src/applications/notifications/controller/base/__init__.php
Normal file
15
src/applications/notifications/controller/base/__init__.php
Normal file
|
@ -0,0 +1,15 @@
|
|||
<?php
|
||||
/**
|
||||
* This file is automatically generated. Lint this module to rebuild it.
|
||||
* @generated
|
||||
*/
|
||||
|
||||
|
||||
|
||||
phutil_require_module('phabricator', 'aphront/response/webpage');
|
||||
phutil_require_module('phabricator', 'applications/base/controller/base');
|
||||
|
||||
phutil_require_module('phutil', 'utils');
|
||||
|
||||
|
||||
phutil_require_source('PhabricatorNotificationsController.php');
|
|
@ -0,0 +1,56 @@
|
|||
<?php
|
||||
|
||||
/*
|
||||
* Copyright 2012 Facebook, Inc.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
final class PhabricatorAphlictTestPageController
|
||||
extends PhabricatorNotificationsController {
|
||||
|
||||
public function processRequest() {
|
||||
|
||||
$instructions = '<h1>Check Your Javascript Console!</h1>';
|
||||
|
||||
$object_id = 'aphlictswfobject';
|
||||
|
||||
$content = phutil_render_tag(
|
||||
'object',
|
||||
array(
|
||||
'classid' => 'clsid:d27cdb6e-ae6d-11cf-96b8-444553540000',
|
||||
),
|
||||
'<param name="movie" value="/rsrc/swf/aphlict.swf" />'.
|
||||
'<param name="allowScriptAccess" value="always" />'.
|
||||
'<embed src="/rsrc/swf/aphlict.swf" id="'.$object_id.'"></embed>');
|
||||
|
||||
Javelin::initBehavior(
|
||||
'aphlict-listen',
|
||||
array(
|
||||
'id' => $object_id,
|
||||
'server' => '127.0.0.1',
|
||||
'port' => 2600,
|
||||
));
|
||||
|
||||
return $this->buildStandardPageResponse(
|
||||
array(
|
||||
$instructions,
|
||||
$content,
|
||||
),
|
||||
array(
|
||||
'title' => 'Aphlict Test Page',
|
||||
));
|
||||
}
|
||||
|
||||
|
||||
}
|
15
src/applications/notifications/controller/test/__init__.php
Normal file
15
src/applications/notifications/controller/test/__init__.php
Normal file
|
@ -0,0 +1,15 @@
|
|||
<?php
|
||||
/**
|
||||
* This file is automatically generated. Lint this module to rebuild it.
|
||||
* @generated
|
||||
*/
|
||||
|
||||
|
||||
|
||||
phutil_require_module('phabricator', 'applications/notifications/controller/base');
|
||||
phutil_require_module('phabricator', 'infrastructure/javelin/api');
|
||||
|
||||
phutil_require_module('phutil', 'markup');
|
||||
|
||||
|
||||
phutil_require_source('PhabricatorAphlictTestPageController.php');
|
|
@ -17,7 +17,6 @@ set -x
|
|||
-output aphlict.swf \
|
||||
-default-background-color=0x444444 \
|
||||
-default-size=500,500 \
|
||||
-target-player=10.2.0 \
|
||||
-warnings=true \
|
||||
-debug=true \
|
||||
-source-path=$ROOT/externals/vegas/src \
|
||||
|
@ -25,3 +24,5 @@ set -x
|
|||
src/Aphlict.as)
|
||||
|
||||
mv $BASEDIR/aphlict.swf $ROOT/webroot/rsrc/swf/aphlict.swf
|
||||
|
||||
# -target-player=10.2.0 \
|
||||
|
|
|
@ -27,9 +27,26 @@ package {
|
|||
private var socket:Socket;
|
||||
private var readBuffer:ByteArray;
|
||||
|
||||
private var remoteServer:String;
|
||||
private var remotePort:Number;
|
||||
|
||||
public function Aphlict() {
|
||||
super();
|
||||
|
||||
ExternalInterface.addCallback('connect', this.externalConnect);
|
||||
ExternalInterface.call(
|
||||
'JX.Stratcom.invoke',
|
||||
'aphlict-component-ready',
|
||||
null,
|
||||
{});
|
||||
}
|
||||
|
||||
public function externalConnect(server:String, port:Number):void {
|
||||
this.externalInvoke('connect');
|
||||
|
||||
this.remoteServer = server;
|
||||
this.remotePort = port;
|
||||
|
||||
this.master = null;
|
||||
this.receiver = new AphlictReceiver(this);
|
||||
this.subjects = [];
|
||||
|
@ -90,25 +107,33 @@ package {
|
|||
|
||||
socket.addEventListener(Event.CONNECT, didConnectSocket);
|
||||
socket.addEventListener(Event.CLOSE, didCloseSocket);
|
||||
socket.addEventListener(IOErrorEvent.IO_ERROR, didErrorSocket);
|
||||
socket.addEventListener(ProgressEvent.SOCKET_DATA, didReceiveSocket);
|
||||
|
||||
socket.connect('127.0.0.1', 2600);
|
||||
socket.addEventListener(IOErrorEvent.IO_ERROR, didIOErrorSocket);
|
||||
socket.addEventListener(
|
||||
SecurityErrorEvent.SECURITY_ERROR,
|
||||
didSecurityErrorSocket);
|
||||
|
||||
socket.connect(this.remoteServer, this.remotePort);
|
||||
|
||||
this.readBuffer = new ByteArray();
|
||||
this.socket = socket;
|
||||
}
|
||||
|
||||
private function didConnectSocket(event:Event):void {
|
||||
this.log("Connect!");
|
||||
this.externalInvoke('connected');
|
||||
}
|
||||
|
||||
private function didCloseSocket(event:Event):void {
|
||||
this.log("Close!");
|
||||
this.externalInvoke('close');
|
||||
}
|
||||
|
||||
private function didErrorSocket(event:Event):void {
|
||||
this.log("Error!");
|
||||
private function didIOErrorSocket(event:IOErrorEvent):void {
|
||||
this.externalInvoke('error', event.text);
|
||||
}
|
||||
|
||||
private function didSecurityErrorSocket(event:SecurityErrorEvent):void {
|
||||
this.externalInvoke('error', event.text);
|
||||
}
|
||||
|
||||
private function didReceiveSocket(event:Event):void {
|
||||
|
@ -126,7 +151,7 @@ package {
|
|||
var msg_len:Number = parseInt(b.readUTFBytes(8), 10);
|
||||
if (b.length >= msg_len + 8) {
|
||||
var bytes:String = b.readUTFBytes(msg_len);
|
||||
var data:Object = JSON.deserialize(bytes);
|
||||
var data:Object = vegas.strings.JSON.deserialize(bytes);
|
||||
var t:ByteArray = new ByteArray();
|
||||
t.writeBytes(b, msg_len + 8);
|
||||
this.readBuffer = t;
|
||||
|
@ -150,11 +175,15 @@ package {
|
|||
}
|
||||
|
||||
public function receiveMessage(msg:Object):void {
|
||||
this.log("Received message!");
|
||||
this.externalInvoke('receive', msg);
|
||||
}
|
||||
|
||||
public function log(msg:String):void {
|
||||
ExternalInterface.call('console.log', msg);
|
||||
public function externalInvoke(type:String, object:Object = null):void {
|
||||
ExternalInterface.call('JX.Aphlict.didReceiveEvent', type, object);
|
||||
}
|
||||
|
||||
public function log(message:String):void {
|
||||
ExternalInterface.call('console.log', message);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -6,7 +6,7 @@ function getFlashPolicy() {
|
|||
'<!DOCTYPE cross-domain-policy SYSTEM ' +
|
||||
'"http://www.macromedia.com/xml/dtds/cross-domain-policy.dtd">',
|
||||
'<cross-domain-policy>',
|
||||
'<allow-access-from domain="*" to-ports="*"/>',
|
||||
'<allow-access-from domain="*" to-ports="2600"/>',
|
||||
'</cross-domain-policy>'
|
||||
].join("\n");
|
||||
}
|
||||
|
|
74
webroot/rsrc/js/application/aphlict/Aphlict.js
Normal file
74
webroot/rsrc/js/application/aphlict/Aphlict.js
Normal file
|
@ -0,0 +1,74 @@
|
|||
/**
|
||||
* @provides javelin-aphlict
|
||||
* @requires javelin-install
|
||||
* javelin-util
|
||||
*/
|
||||
|
||||
/**
|
||||
* Simple JS API for the Flash Aphlict client. Example usage:
|
||||
*
|
||||
* var aphlict = new JX.Aphlict('aphlict_swf', '127.0.0.1', 2600)
|
||||
* .setHandler(function(type, message) {
|
||||
* JX.log("Got " + type + " event!")
|
||||
* })
|
||||
* .start();
|
||||
*
|
||||
* Your handler will receive these events:
|
||||
*
|
||||
* - `connect` The client initiated a connection to the server.
|
||||
* - `connected` The client completed a connection to the server.
|
||||
* - `close` The client disconnected from the server.
|
||||
* - `error` There was an error.
|
||||
* - `receive` Received a message from the server.
|
||||
*
|
||||
* You do not have to handle any of them in any specific way.
|
||||
*/
|
||||
JX.install('Aphlict', {
|
||||
|
||||
construct : function(id, server, port) {
|
||||
if (__DEV__) {
|
||||
if (JX.Aphlict._instance) {
|
||||
JX.$E('Aphlict object is sort of a singleton..!');
|
||||
}
|
||||
}
|
||||
|
||||
JX.Aphlict._instance = this;
|
||||
|
||||
this._server = server;
|
||||
this._port = port;
|
||||
|
||||
// Flash puts its "objects" into global scope in an inconsistent way,
|
||||
// because it was written in like 1816 when globals were awesome and IE4
|
||||
// didn't support other scopes since global scope is the best anyway.
|
||||
var container = document[id] || window[id];
|
||||
|
||||
this._flashContainer = container;
|
||||
},
|
||||
|
||||
members : {
|
||||
_server : null,
|
||||
_port : null,
|
||||
start : function() {
|
||||
this._flashContainer.connect(this._server, this._port);
|
||||
}
|
||||
},
|
||||
|
||||
properties : {
|
||||
handler : null
|
||||
},
|
||||
|
||||
statics : {
|
||||
_instance : null,
|
||||
didReceiveEvent : function(type, message) {
|
||||
if (!JX.Aphlict._instance) {
|
||||
return;
|
||||
}
|
||||
|
||||
var handler = JX.Aphlict._instance.getHandler();
|
||||
if (handler) {
|
||||
handler(type, message);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
});
|
|
@ -0,0 +1,30 @@
|
|||
/**
|
||||
* @provides javelin-behavior-aphlict-listen
|
||||
* @requires javelin-behavior
|
||||
* javelin-aphlict
|
||||
* javelin-util
|
||||
* javelin-stratcom
|
||||
*/
|
||||
|
||||
JX.behavior('aphlict-listen', function(config) {
|
||||
function onready() {
|
||||
JX.log("The flash component is ready!");
|
||||
|
||||
var client = new JX.Aphlict(config.id, config.server, config.port)
|
||||
.setHandler(function(type, message) {
|
||||
if (message) {
|
||||
JX.log("Got aphlict event '" + type + "':");
|
||||
JX.log(message);
|
||||
} else {
|
||||
JX.log("Got aphlict event '" + type + "'.");
|
||||
}
|
||||
})
|
||||
.start();
|
||||
}
|
||||
|
||||
|
||||
// Wait for the element to load, and don't do anything if it never loads.
|
||||
// If we just go crazy and start making calls to it before it loads, its
|
||||
// interfaces won't be registered yet.
|
||||
JX.Stratcom.listen('aphlict-component-ready', null, onready);
|
||||
});
|
Binary file not shown.
Loading…
Reference in a new issue