Skip to content

Commit

Permalink
Merge pull request #50 from amos-ws16/dev
Browse files Browse the repository at this point in the history
Sprint 07 Release
  • Loading branch information
jhuenges committed Dec 8, 2016
2 parents 3e6b139 + 38a3ba9 commit 85aee25
Show file tree
Hide file tree
Showing 18 changed files with 239 additions and 214 deletions.
10 changes: 9 additions & 1 deletion CHANGELOG.md
@@ -1,7 +1,15 @@
# Change Log
All notable changes to this project will be documented in this file.

## [Unreleased](https://github.com/amos-ws16/amos-ws16-arrowjs/compare/midproject-release...dev)
## [Unreleased](https://github.com/amos-ws16/amos-ws16-arrowjs/compare/sprint-07-release...dev)

## [1.4.0](https://github.com/amos-ws16/amos-ws16-arrowjs/releases/tag/sprint-07-release) - 2016-12-08

## Changed
- Updated [Getting Started](https://github.com/amos-ws16/amos-ws16-arrowjs/blob/master/docs/user-guide.md) to include custom configurations

## Removed
- `similar-title-plugin` and `same-title-plugin` and refactored the functionality into the `similar-context-plugin`

## [1.3.0](https://github.com/amos-ws16/amos-ws16-arrowjs/releases/tag/midproject-release) - 2016-12-01

Expand Down
6 changes: 3 additions & 3 deletions config/index.js
Expand Up @@ -14,9 +14,9 @@ config.scoreManager = {
aggregator: new aggregator.Mean(),
plugins: {
// similar-title-plugin pulls file.title from file and tasks[].title from tasks[] itself
'similar-title': {
use: 'similar-title-plugin',
inputs: ['file', 'tasks[]']
'similar-file-title-task-title': {
use: 'similar-context-plugin',
inputs: ['file.title', 'tasks[].title']
},
// timestamp comparison defaults to 600 sec
'context-file-timestamp-tasks-timestamp': {
Expand Down
131 changes: 114 additions & 17 deletions docs/user-guide.md
@@ -1,17 +1,17 @@
#User guide for the ARROW API
# User guide for the ARROW API


##1. Introduction
## 1. Introduction

This user guide explains how to use the ARROW API with the basic configuration. It declares all functions of the API, how to use them and give examples for requests and their results.
This user guide explains how to use the ARROW API with the basic configuration. It declares all functions of the API, how to use them and gives examples for requests and their results.

##2. Requests
## 2. Requests

The ARROW API is based on REST principles: data resources are accessed via standard HTTP requests in UTF-8 format to an API endpoint. The API is running on a server hosted by amazon AWS. To use this API you have to send a POST request to the following address:
The ARROW API is based on REST principles: data resources are accessed via standard HTTP requests in UTF-8 format to an API endpoint. The API is running on a server hosted by amazon AWS. To use this API you have to send a POST request to the following address:

http://ec2-52-212-74-103.eu-west-1.compute.amazonaws.com:4000/api/score

##3. Input scheme
## 3. Input scheme

All data is received as a JSON object that are based on the following scheme:

Expand Down Expand Up @@ -40,27 +40,25 @@ All data is received as a JSON object that are based on the following scheme:
}
```

The fields marked with (required) are necessary for the comparison. If one or more of these fields are missing the API will return an exception.
The fields marked with '(required)' are necessary for the comparison. If one or more of these fields are missing the API will return an exception.

##4. Functions
## 4. Functions

There are three important concepts that facilitate assigning a score to tasks representing the degree to which they match an uploaded file and its metadata: The Score Manager, one or more Plugins and an Aggregator.
A Plugin is a function that takes two arguments - a file object that contains meta data, for example the filename, size, time of upload and/or the file contents, and a task object that contains meta data related to the task, for example the task name. It returns a floating point numeric score in the range 0.0 to 1.0 which describes the degree in which the file and the task are correlated in the aspect that this plugin is focused on. There are 4 Plugins available:
1. The same-title Plugin:
This plugin checks if the title of the file object is equal to the title of the task. If the titles are the same this plugin will return 1.0 otherwise the result would be 0.0.

2. The similar-title Plugin:
The similar-title plugin checks the titles of the file object and the task and compares them. If they are not completely equal but nearly the same, the plugin would return a value near to 1.0.
1. The similar-context Plugin:
This plugin different types of texts like descriptions or titles of files and tasks. If the content of the two texts are similar but have different descriptions, the result would be about 1.0. For information on available parameters take a look at the [source](https://github.com/amos-ws16/amos-ws16-arrowjs/blob/dev/lib/plugins/similar-context-plugin.js).


2. The close-time Plugin:
It checks the time, when both objects were uploaded (or updated) and if the upload times are far away from each other the plugin would return 0.0. Otherwise if the objects are uploaded at the same time the result would be 1.0. For information on available parameters take a look at the [source](https://github.com/amos-ws16/amos-ws16-arrowjs/blob/master/lib/plugins/close-time-plugin.js).

3. The similar-context Plugin:
This plugin compares large texts like descriptions of files and tasks. If the content of the two texts are similar but have different descriptions, the result would be about 1.0

4. The close-time Plugin:
It checks the time, when both objects were uploaded (or updated) and if the upload times are far away from each other the plugin would return 0.0. Otherwise if the objects are uploaded at the same time the result would be 1.0.
An Aggregator is a policy that combines a set of scores that were previously assigned to a task by multiple Plugins into a single final score value. For example, if the score of the close-time Plugin is 1.0 and the score of the similar-title Plugin is 0.0 the combined value would be 0.5.
The purpose of the Score Manager is to provide the entry point for a scoring request, delegate the data to multiple Plugins, and combine their individual scores using an Aggregator.

5. Example
## 5. Example

Request:
```json
Expand Down Expand Up @@ -92,3 +90,102 @@ Request:
}
```

## 6. Configuration

The Basic-Configuration of this API makes 5 different comparisons:

1. Similar Title:
Compares the title of the file with all task titles

2. Context File Timestamp - Tasks Timestamp:
Compares the timestamps of file and tasks with a time limit of 600 seconds

3. Context File Timestamp - Tasks Timestamp (Long):
Compares the timestamps of file and tasks with a time limit of 3000 seconds

4. Context File Description - Task Title:
Compares the description of a file with the title of tasks

5. Context File Description - Task Description:
Compares the description of a file with the description of tasks

There is also the possibility to configure the API by yourself, just by sending an own configuration with the Post Request. To create an own configuration for this API, define a name of what is compared, the plugin that is used and the input fields which are compared. Optionally there is the possibility to add several parameters. An example could look like this:

```json
"plugins":{
"context-file-description-task-description": {
"use": "similar-context-plugin",
"inputs": ["file.description", "tasks[].description"],
"params": { "extractKeywords": true }
}
```

This configuration is used to compare the description of file and tasks (`"inputs": ["file.description", "tasks[].description"]`) by keywords (`"params": { "extractKeywords": true }`) with the similar context (`"use": "similar-context-plugin"`) plugin.

After defining the used plugins, the score aggregator must be configured. There are 3 different types of aggregators:

1. The Mean Aggregator:
This aggregator combines scores by calculating the average of all scores.
It can be used with the keyword `Mean`

2. The Largest Aggregator:
Is an aggregator that combines scores by choosing the biggest score out of all scores. It can be used with the keyword `Largest`

3. The Weighted Mean Aggregator:
Combines scores by calculating the weighted average of all scores
It can be used with the keyword `WeightedMean`

Example for custom configuration:
```json
{
"config": {
"aggregator": "Mean",
"plugins": {
"context-file-description-task-description": {
"use": "similar-context-plugin",
"inputs": ["file.description", "tasks[].description"],
"params": {
"extractKeywords": true
}
}
}
},
"file": {
"title": "Cafe abc",
"type": "jpeg",
"created_at": 1479755100,
"user": "5hj34thtr",
"description": " Great location for a meeting"
},
"tasks": [{
"title": " find a location",
"created_at": 1479754800,
"due_date": 1479766305,
"created_by": "ikgDG94s",
"description": "Find a location for the next meeting"
}, {
"title": " Check your mails",
"created_at": 1379754800,
"due_date": 1454353454,
"created_by": "dfgj2s334",
"description": "Check your mails before you leave."
}]
}
```

Example response for the request:
```json
{
"success": true,
"result": [
{
"context-file-description-task-description": 0.7878787878787878,
"total": 0.7878787878787878
},
{
"context-file-description-task-description": 0.06896551724137931,
"total": 0.06896551724137931
}
]
}
```
Binary file removed docs/user-guide.pdf
Binary file not shown.
14 changes: 0 additions & 14 deletions lib/plugins/same-title-plugin.js

This file was deleted.

7 changes: 4 additions & 3 deletions lib/plugins/similar-context-plugin.js
Expand Up @@ -8,9 +8,10 @@ const utils = require('../utils.js')
*
* If param 'extractKeywords' is true: first uses the keyword-extractor to get the keywords, then compares the keywords with stringSimilarity to get a context score
*
* @param file - the file with its description
* @param task - the task with its description
* @param params - object with attribute extractKeywords as parameter for extracting the keywords (true - extract keyword before calculating similarity score, false - whithout extraction)
* @param sString1 - first string for comparison
* @param sString2 - second string for comparison
* @param params - object with attribute:
* 'extractKeywords' as parameter for extracting the keywords (true - extract keyword before calculating similarity score, false - whithout extraction)
*/
function similarityPlugin (sString1, sString2, params) {
let extractKeywords = (params && params['extractKeywords']) || false
Expand Down
17 changes: 0 additions & 17 deletions lib/plugins/similar-title-plugin.js

This file was deleted.

2 changes: 1 addition & 1 deletion lib/score-manager.js
Expand Up @@ -133,7 +133,7 @@ function getAggregator (aggregator) {
* task, for example the task name. It returns a floating point numeric score
* in the range 0.0 to 1.0 which describes the degree in which the file and
* the task are correlated in the aspect that this particular Plugin is focused
* on. For example, the `same-title` Plugin will return 1.0 if the title of the
* on. For example, the `similar-context` Plugin will return 1.0 if the title of the
* file is the same as the title of the task and 0.0 otherwise.
*
* An Aggregator is a policy that combines a set of scores that were previously
Expand Down
19 changes: 17 additions & 2 deletions lib/server/post-api-score.js
@@ -1,3 +1,5 @@
const VError = require('verror').VError

const config = require('../../config')
const scoreManager = require('../score-manager')

Expand All @@ -6,8 +8,21 @@ const scoreManager = require('../score-manager')
*/
function postApiScore (req, res) {
let requestConfig = req.body.config || config.scoreManager
let manager = scoreManager.create(requestConfig)
res.json(manager.score(req.body))
try {
let manager = scoreManager.create(requestConfig)
let result = manager.score(req.body)

// If there was no exception up to this point, we have success.
res.json({ success: true, result: result })
} catch (err) {
if (VError.hasCauseWithName(err, 'InvalidInputError')) {
res.json({ success: false, error: err.message })
return
}

res.json({ success: false, error: 'Internal Server Error' })
throw err
}
}

module.exports = postApiScore
14 changes: 1 addition & 13 deletions lib/utils.js
@@ -1,15 +1,3 @@
/**
* Returns the basename without extension of filename. If the filename does not
* contain any dots it will be returned as is, otherwise the extension is
* stripped and the basename is returned.
*
* @param filename - name of a file basename.ext
*/
function basename (filename) {
let dotPosition = filename.lastIndexOf('.')
return dotPosition === -1 ? filename : filename.substring(0, dotPosition)
}

/**
* Returns a copy of the given object. The object must be serializable to
* JSON, thus cloning will only work on primitive objects.
Expand Down Expand Up @@ -63,4 +51,4 @@ function isTimestamp (timest) {
}
}

module.exports = { basename, cloneObject, isValidString, isInRange, isInteger, isTimestamp }
module.exports = { cloneObject, isValidString, isInRange, isInteger, isTimestamp }
2 changes: 1 addition & 1 deletion package.json
@@ -1,6 +1,6 @@
{
"name": "arrow",
"version": "1.3.1",
"version": "1.4.0",
"description": "Description that needs to be changed some time soon",
"license": "AGPL-3.0",
"repository": "https://github.com/amos-ws16/amos-ws16-arrowjs",
Expand Down
36 changes: 0 additions & 36 deletions test/api-test.js

This file was deleted.

3 changes: 0 additions & 3 deletions test/buster.js
Expand Up @@ -3,9 +3,6 @@ var config = module.exports
config['My tests'] = {
rootPath: '../',
environment: 'node', // or 'browser'
sources: [
'lib/**/*.js'
],
tests: [
'test/**/*-test.js'
]
Expand Down

0 comments on commit 85aee25

Please sign in to comment.