Skip to content

Commit 2a45e36

Browse files
2.0 (#23)
* Move clients into their own repository * Introduce INF/NAN string values normalizer (#19) * Introduce INF/NAN string values normalizer * Introduce INF/NAN string values normalizer * Update CHANGELOG * Fix CS Co-authored-by: Andrew DalPino <andrewdalpino@users.noreply.github.com> * Rename convert constants middleware * Refactor convert sample constants middleware * Upgrade ML to 2.0 (#20) * Appease Stan --------- Co-authored-by: Alex Torchenko <torchenko@gmail.com>
1 parent 852dc1a commit 2a45e36

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

50 files changed

+237
-994
lines changed

CHANGELOG.md

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,11 @@
1+
- 2.0.0
2+
- Move clients into their own repository
3+
- INF and NAN string sample values are automatically converted to respective PHP constants
4+
15
1.0.1
26
- Do not use deprecated ReactPHP class names
37

4-
1.0.0
8+
- 1.0.0
59
- Add pan and zoom to dashboard charts
610
- Rename anomaly scores HTTP resource
711

README.md

Lines changed: 11 additions & 173 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,8 @@
11
# Rubix Server
2-
Rubix Server is a library for bringing your trained [Rubix ML](https://github.com/RubixML/ML) models into production. Inference servers are stand-alone services that run on your private or public network and wrap your trained estimator in an API that can be queried locally or over the network in real-time using standard protocols. In addition, the library provides async-compatible client implementations for making queries to the server from your PHP applications.
2+
Rubix Server is a library for deploying your [Rubix ML](https://github.com/RubixML/ML) models to production. Our server wraps your trained estimator in an API that can be queried using standard protocols. Included is a real-time dashboard for monitoring the health and throughput of your models.
33

44
- **Optimized** for low latency predictions
5-
- **Scalable** horizontally by adding more instances
5+
- **Scale** by adding more instances
66
- **Monitoring** with real-time analytics dashboard
77
- **Robust** to common threats and failure modes
88

@@ -20,7 +20,7 @@ A [Docker Image](https://gitlab.com/torchello/rubix-ml-server-docker) is availab
2020
- [PHP](https://php.net/manual/en/install.php) 7.4 or above
2121

2222
## Documentation
23-
The latest documentation can be found below.
23+
The latest documentation can be found in this README.
2424

2525
### Table of Contents
2626
- [Servers](#servers)
@@ -30,13 +30,6 @@ The latest documentation can be found below.
3030
- [Basic Authenticator](#basic-authenticator)
3131
- [Shared Token Authenticator](#shared-token-authenticator)
3232
- [Trusted Clients](#trusted-clients)
33-
- [Clients](#clients)
34-
- [REST Client](#rest-client)
35-
- [Client Middleware](#client-middleware)
36-
- [Backoff and Retry](#backoff-and-retry)
37-
- [Basic Authenticator](#basic-authenticator-client-side)
38-
- [Compress Request Body](#compress-request-body)
39-
- [Shared Token Authenticator](#shared-token-authenticator-client-side)
4033
- [Loggers](#loggers)
4134
- [File](#file)
4235
- [FAQs](#faqs)
@@ -124,9 +117,9 @@ Interfaces: [Server](#servers), [Verbose](#verbose-interface)
124117

125118
```php
126119
use Rubix\Server\HTTPServer;
127-
use Rubix\Server\HTTP\Middleware\Server\AccessLogGenerator;
120+
use Rubix\Server\HTTP\Middleware\\AccessLogGenerator;
128121
use Rubix\Server\Loggers\File;
129-
use Rubix\Server\HTTP\Middleware\Server\BasicAuthenticator;
122+
use Rubix\Server\HTTP\Middleware\\BasicAuthenticator;
130123
use Rubix\Server\Services\Caches\InMemoryCache;
131124

132125
$server = new HTTPServer('127.0.0.1', 443, '/cert.pem', [
@@ -178,7 +171,7 @@ Generates an HTTP access log using a format similar to the Apache log format.
178171
**Example**
179172

180173
```php
181-
use Rubix\Server\HTTP\Middleware\Server\AccessLog;
174+
use Rubix\Server\HTTP\Middleware\\AccessLog;
182175
use Rubix\Server\Loggers\File;
183176

184177
$middleware = new AccessLog(new File('access.log'));
@@ -203,7 +196,7 @@ An implementation of HTTP Basic Auth as described in [RFC7617](https://tools.iet
203196
**Example**
204197

205198
```php
206-
use Rubix\Server\HTTP\Middleware\Server\BasicAuthenticator;
199+
use Rubix\Server\HTTP\Middleware\\BasicAuthenticator;
207200

208201
$middleware = new BasicAuthenticator([
209202
'morgan' => 'secret',
@@ -225,7 +218,7 @@ Authenticates incoming requests using a shared key that is kept secret between t
225218
**Example**
226219

227220
```php
228-
use Rubix\Server\HTTP\Middleware\Server\SharedTokenAuthenticator;
221+
use Rubix\Server\HTTP\Middleware\\SharedTokenAuthenticator;
229222

230223
$middleware = new SharedTokenAuthenticator([
231224
'secret', 'another-secret',
@@ -243,172 +236,17 @@ A whitelist of clients that can access the server - all other connections will b
243236
**Example**
244237

245238
```php
246-
use Rubix\Server\HTTP\Middleware\Server\TrustedClients;
239+
use Rubix\Server\HTTP\Middleware\\TrustedClients;
247240

248241
$middleware = new TrustedClients([
249242
'127.0.0.1', '192.168.4.1', '45.63.67.15',
250243
]);
251244
```
252245

253-
---
254-
### Clients
255-
Clients allow you to communicate directly with a model server using a friendly object-oriented interface inside your PHP applications. Under the hood, clients handle all the networking communication and content negotiation for you so you can write programs *as if* the model was directly accessible in your applications.
256-
257-
Return the predictions from the model:
258-
```php
259-
public predict(Dataset $dataset) : array
260-
```
261-
262-
```php
263-
use Rubix\Server\RESTClient;
264-
265-
$client = new RESTClient('127.0.0.1', 8080);
266-
267-
// Import a dataset
268-
269-
$predictions = $client->predict($dataset);
270-
```
271-
272-
Calculate the joint probabilities of each sample in a dataset:
273-
```php
274-
public proba(Dataset $dataset) : array
275-
```
276-
277-
Calculate the anomaly scores of each sample in a dataset:
278-
```php
279-
public score(Dataset $dataset) : array
280-
```
281-
282-
### Async Clients
283-
Clients that implement the Async Client interface have asynchronous versions of all the standard client methods. All asynchronous methods return a [Promises/A+](https://promisesaplus.com/) object that resolves to the return value of the response. Promises allow you to perform other work while the request is processing or to execute multiple requests in parallel. Calling the `wait()` method on the promise will block until the promise is resolved and return the value.
284-
285-
```php
286-
public predictAsync(Dataset $dataset) : Promise
287-
```
288-
289-
```php
290-
$promise = $client->predictAsync($dataset);
291-
292-
// Do something else
293-
294-
$predictions = $promise->wait();
295-
```
296-
297-
Return a promise for the probabilities predicted by the model:
298-
```php
299-
public probaAsync(Dataset $dataset) : Promise
300-
```
301-
302-
Return a promise for the anomaly scores predicted by the model:
303-
```php
304-
public scoreAsync(Dataset $dataset) : Promise
305-
```
306-
307-
### REST Client
308-
The REST Client communicates with the [HTTP Server](#http-server) through the JSON REST API it exposes.
309-
310-
Interfaces: [Client](#clients), [AsyncClient](#async-clients)
311-
312-
#### Parameters
313-
| # | Param | Default | Type | Description |
314-
|---|---|---|---|---|
315-
| 1 | host | '127.0.0.1' | string | The IP address or hostname of the server. |
316-
| 2 | port | 8000 | int | The network port that the HTTP server is running on. |
317-
| 3 | secure | false | bool | Should we use an encrypted HTTP channel (HTTPS)? |
318-
| 4 | middlewares | | array | The stack of client middleware to run on each request/response. |
319-
| 5 | timeout | | float | The number of seconds to wait before giving up on the request. |
320-
| 6 | verify certificate | true | bool | Should we try to verify the server's TLS certificate? |
321-
322-
**Example**
323-
324-
```php
325-
use Rubix\Server\RESTClient;
326-
use Rubix\Server\HTTP\Middleware\Client\BasicAuthenticator;
327-
use Rubix\Server\HTTP\Middleware\Client\CompressRequestBody;
328-
use Rubix\Server\HTTP\Middleware\Client\BackoffAndRetry;
329-
use Rubix\Server\HTTP\Encoders\Gzip;
330-
331-
$client = new RESTClient('127.0.0.1', 443, true, [
332-
new BasicAuthenticator('user', 'password'),
333-
new CompressRequestBody(new Gzip(1)),
334-
new BackoffAndRetry(),
335-
], 0.0, true);
336-
```
337-
338-
### Client Middleware
339-
Similarly to Server middleware, client middlewares are functions that hook into the request/response cycle but from the client end. Some of the server middlewares have accompanying client middleware such as [Basic Authenticator](#basic-authenticator) and [Shared Token Authenticator](#shared-token-authenticator).
340-
341-
### Backoff and Retry
342-
The Backoff and Retry middleware handles Too Many Requests (429) and Service Unavailable (503) responses by retrying the request after waiting for a period of time to avoid overloading the server even further. An acceptable backoff period is gradually achieved by multiplicatively increasing the delay between retries.
343-
344-
#### Parameters
345-
| # | Param | Default | Type | Description |
346-
|---|---|---|---|---|
347-
| 1 | max retries | 3 | int | The maximum number of times to retry the request before giving up. |
348-
| 2 | initial delay | 0.5 | float | The number of seconds to delay between retries before exponential backoff is applied. |
349-
350-
**Example**
351-
352-
```php
353-
use Rubix\Server\HTTP\Middleware\Client\BackoffAndRetry;
354-
355-
$middleware = new BackoffAndRetry(5, 0.5);
356-
```
357-
358-
### Basic Authenticator (Client Side)
359-
Adds the necessary authorization headers to the request using the Basic scheme.
360-
361-
#### Parameters
362-
| # | Param | Default | Type | Description |
363-
|---|---|---|---|---|
364-
| 1 | username | | string | The user's name. |
365-
| 2 | password | | string | The user's password. |
366-
367-
**Example**
368-
369-
```php
370-
use Rubix\Server\HTTP\Middleware\Client\BasicAuthenticator;
371-
372-
$middleware = new BasicAuthenticator('morgan', 'secret');
373-
```
374-
375-
### Compress Request Body
376-
Apply the Gzip compression algorithm to the request body.
377-
378-
#### Parameters
379-
| # | Param | Default | Type | Description |
380-
|---|---|---|---|---|
381-
| 1 | level | 1 | int | The compression level between 0 and 9 with 0 meaning no compression. |
382-
| 2 | threshold | 65535 | int | The minimum size of the request body in bytes in order to be compressed. |
383-
384-
**Example**
385-
386-
```php
387-
use Rubix\Server\HTTP\Middleware\Client\CompressRequestBody;
388-
389-
$middleware = new CompressRequestBody(5, 65535);
390-
```
391-
392-
### Shared Token Authenticator (Client Side)
393-
Adds the necessary authorization headers to the request using the Bearer scheme.
394-
395-
#### Parameters
396-
| # | Param | Default | Type | Description |
397-
|---|---|---|---|---|
398-
| 1 | token | | string | The shared token to authenticate the request. |
399-
400-
**Example**
401-
402-
```php
403-
use Rubix\Server\HTTP\Middleware\Client\SharedtokenAuthenticator;
404-
405-
$middleware = new SharedTokenAuthenticator('secret');
406-
```
407-
408-
### Loggers
246+
## Loggers
409247
PSR-3 compatible loggers for capturing important server events.
410248

411-
#### File
249+
### File
412250
A simple append-only file logger.
413251

414252
#### Parameters

composer.json

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
{
22
"name": "rubix/server",
33
"type": "library",
4-
"description": "Serve your Rubix ML models in production with scalable stand-alone model servers.",
4+
"description": "Deploy your Rubix ML models to production with scalable stand-alone inference servers.",
55
"homepage": "https://github.com/RubixML/Server",
66
"license": "MIT",
77
"readme": "README.md",
@@ -26,22 +26,21 @@
2626
],
2727
"require": {
2828
"php": ">=7.4",
29-
"guzzlehttp/guzzle": "^7.2",
3029
"guzzlehttp/psr7": "^1.7",
3130
"psr/container": "^1.1",
3231
"psr/http-message": "^1.0",
3332
"psr/log": "^1.1",
3433
"react/http": "^1.1",
35-
"rubix/ml": "^1.0",
34+
"rubix/ml": "^2.0",
3635
"symfony/polyfill-php80": "^1.17",
3736
"webonyx/graphql-php": "^14.4"
3837
},
3938
"require-dev": {
4039
"friendsofphp/php-cs-fixer": "^3.0",
41-
"phpstan/phpstan": "0.12.*",
40+
"phpstan/phpstan": "^1.0",
4241
"phpstan/extension-installer": "^1.0",
43-
"phpstan/phpstan-phpunit": "0.12.*",
44-
"phpunit/phpunit": "8.5.*"
42+
"phpstan/phpstan-phpunit": "^1.0",
43+
"phpunit/phpunit": "^9.0"
4544
},
4645
"autoload": {
4746
"psr-4": {
@@ -70,7 +69,10 @@
7069
},
7170
"config": {
7271
"preferred-install": "dist",
73-
"sort-packages": true
72+
"sort-packages": true,
73+
"allow-plugins": {
74+
"phpstan/extension-installer": true
75+
}
7476
},
7577
"funding": [
7678
{

examples/HTTP/client.php

Lines changed: 0 additions & 30 deletions
This file was deleted.

examples/HTTP/server.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,8 @@
66
use Rubix\ML\Datasets\Generators\Agglomerate;
77
use Rubix\ML\Classifiers\GaussianNB;
88
use Rubix\Server\HTTPServer;
9-
use Rubix\Server\HTTP\Middleware\Server\AccessLogGenerator;
10-
use Rubix\Server\HTTP\Middleware\Server\BasicAuthenticator;
9+
use Rubix\Server\HTTP\Middleware\AccessLogGenerator;
10+
use Rubix\Server\HTTP\Middleware\BasicAuthenticator;
1111
use Rubix\Server\Services\Caches\InMemoryCache;
1212
use Rubix\ML\Loggers\Screen;
1313

phpstan.neon

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,3 +3,4 @@ parameters:
33
paths:
44
- 'src'
55
- 'tests'
6+
checkGenericClassInNonGenericObjectType: false

src/AsyncClient.php

Lines changed: 0 additions & 33 deletions
This file was deleted.

0 commit comments

Comments
 (0)