Giter Club home page Giter Club logo

commonality / archetypes-rules Goto Github PK

View Code? Open in Web Editor NEW
13.0 3.0 3.0 7.76 MB

A JavaScript rule engine that models formal propositional logic. It allows you to separate conditional logic from source code and database triggers in a reusable package, where explicit rules can be independently defined and managed.

License: MIT License

Shell 1.38% JavaScript 98.62%
rules rules-engine archetype-pattern boolean-logic rpn rule-context facts json rule-overrides rule-sets

archetypes-rules's Introduction

archetypes-rules

banner

The MIT License NPM version FOSSA Status Known Vulnerabilities
Dependency Status
MacOS and Ubuntu build statuses Windows build status Coveralls test coverage Codacy code quality

Move conditional logic out of source code and database triggers and into a reusable package, where explicit rules can be independently defined and managed.

archetypes-rules models Boolean logic. Instead of writing conditionals like if / else if / else, you can instead create Rules that describe and evaluate Facts (aka, RuleContexts).

Table of Contents

1. Overview

Figure 1: Class diagram for the archetypes.rules namespace.

Figure 1: Class diagram for the archetypes.rules namespace

1.1. Rules

Rules are explicit constraints that govern actions. Rules evaluate Facts, or RuleContexts.

Rules are defined with⏤and stored as⏤JSON.

1.2. RuleElements

Rules contain one or more RuleElements. There are three types of RuleElements: Propositions, Operators, and Variables.

1.2.1. Propositions

Propositions are statements that are either, true, false, or null (unknown). Learn more...

1.2.2. Variables

Variables are symbols that represent the value of something. Learn more...

1.2.3. Operators

Operators: Boolean and quantifier operators.

1.3. RuleContexts (aka "facts")

RuleContexts are facts, stored as JSON in files, databases, etc.

1.4. Rules evaluate RuleContexts/Facts

Rules evaluate RuleContexts. During evaluation, we determine whether a RuleContext/Fact complies with a Rule.

returning a Proposition that tells us whether a given set of facts conform to the defined Rule.

RuleElements are evaluated using Reverse Polish Notation (RPN). See the examples below for details.

Back to Table of contents [toc]

2. Installation

npm install archetypes-rules

Back to Table of contents [toc]

3. Usage

3.1. Example 1: Is this customer eligible for a discount

Suppose we have a very simple rule that checks whether a customer is eligible for a discount. In order to be eligible, the customer simply needs to be a Gold Card holder.

const { Rule, RuleContext } = require('archetypes-rules')

// Create the rule
const rule = new Rule('eligibleForDiscount')

// Add a Proposition, i.e., a statement that has a value of true or false
rule.addProposition('customerIsGoldCardHolder', true)

// Create a RuleContext, i.e., a "Fact"
const ruleContext = RuleContext('eligibleForDiscountContext')

// Provide the truth statement as to whether the actual customer
// has a Gold Card
ruleContext.addProposition('customerIsGoldCardHolder', true)

// Evaluate
const result = rule.evaluate(ruleContext)

// Log the resulting Proposition

// Outputs
// Proposition statement = customerIsGoldCardHolder, value = true

3.2. Example 2: Group discount for six or more people

Say you provide a discount to a group of six or more people:

// Create the rule
const rule = Rule('eligible-for-group-discount')

// Declare a "placeholder" variable for the actual number of people
// (This value will be retrieved from the RuleContext)
rule.addVariable('actual-num-people', null)

// Declare the minimum number of people required for discount
rule.addVariable('min-num-people', 6)

// Compare the two, i.e.,
// actual-num-people >= min-num-people
rule.addOperator(Operator.GREATER_THAN_OR_EQUAL_TO)

// Create a RuleContext, i.e., a "Fact"
const ruleContext = RuleContext('eligible-for-group-discount-fact')

// How many people are there?
ruleContext.addVariable('actual-num-people', 5)

// Declare the "placeholder" minimun number of people required for discount
// (This value will be retrieved from the Rule)
ruleContext.addVariable('min-num-people', 'NULL_NUMBER_VARIABLE')

// Evaluate
const result = rule.evaluate(ruleContext)

// Log the resulting Proposition

// OUTPUT:
// Proposition statement =
// (actualNumPeople >= minNumPeople), value = false

3.3. Example 3: Is an airline passenger eligible for an upgrade?

In this example, we’re determining whether a given airline passenger is eligible to have their coach seat upgraded to a first-class seat. In order to be eligible, a passenger must:

  • Be in economy class now and either
    • Hold a Gold member card or
    • Hold a Silver member card and
  • Their carry-on luggage must be less than or equal to 15.0 pounds.

In order to determine this, we must compare a passenger’s facts with our rule.

const { Rule, RuleContext, RuleElement } = require('archetypes-rules')

// Create the rule
const rule = Rule('eligible-for-upgrade')

// Populate the rule using method chaining
rule
  .addProposition('passenger-is-economy', true)
  .addProposition('passenger-is-gold-card-holder', true)
  .addProposition('passenger-is-silver-card-holder', true)
  .addOperator('OR')
  .addOperator('AND')
  .addVariable('passenger-carry-on-baggage-weight', 'NULL_NUMBER_VARIABLE')
  .addVariable('passenger-carry-on-baggage-allowance', 15.0)
  .addOperator('LESS_THAN_OR_EQUAL_TO')
  .addOperator('AND')

// Create the RuleContext
const fact = RuleContext('eligibleForUpgradeFact')

// Load it with the facts about the passenger
fact
  .addProposition('passengerIsEconomy', true)
  .addProposition('passengerIsGoldCardHolder', true)
  .addProposition('passengerIsSilverCardHolder', false)
  .addVariable('passenger-carry-on-baggage-weight', 10.0)
  .addVariable('passenger-carry-on-baggage-allowance', 'NULL_NUMBER_VARIABLE')

// Log the resulting Proposition

// =>
// Proposition statement = (
//  (passengerIsEconomy AND
//    (passengerIsGoldCardHolder OR passengerIsSilverCardHolder)
//  ) AND (
//    passenger-carry-on-baggage-weight <= passenger-carry-on-baggage-allowance
//  )
// ), value = true

Back to Table of contents [toc]

4. Maintainers

@gregswindle

Information for Maintainers The Maintainer Guide describes how we develop and release archetype-rules (and has useful information for Maintainers and Trusted Committers).

Back to Table of contents [toc]

5. Contributions

GitHub Contributors GitHub GitHub Greenkeeper badge

Gratitude We gratefully accept Pull Requests. Here's what you need to know to get started.

Before submitting a Pull Request, please read our:

Back to Table of contents [toc]

6. License

MIT © 2019 Greg Swindle

Open Source Licenses View the latest detailed legal NOTICE report This link will take you to another Web site.

FOSSA Status

Back to Table of contents [toc]

archetypes-rules's People

Contributors

dependabot-preview[bot] avatar dependabot[bot] avatar gregswindle avatar semantic-release-bot avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar

Forkers

fossabot fgcp020

archetypes-rules's Issues

refactoring: remove redundant lodash functions

code Refactoring proposal

1. Design summary / code smell(s)

The production dependency @sindresorhus/is fulfills most, if not all, required checks currently enforced with lodash.is* functions.

2. Refactoring proposal(s)

Favor @sindresorhus/is over lodash, which should reduce the library's size and make it easier to maintain.

  1. Remove as many lodash.is* functions, and use is.* instead.

    Example:

    // Instead of:
    isString(variable)
    
    // Use:
    is.string(variable)

3. Code quality improvement scores Sonar Quality Gate

  • The refactorings changes have either:

    • Reduced complexity, duplications, issues, security issues;
    • Improved maintainability or reliability; or
    • Both.

Code quality results summary

Measure Scores
Quality gate Sonar Alert Status Metrics
Defects (Bugs) Sonar Bugs Metrics
Duplications Sonar Duplicated Lines Density Metrics
Maintainability Sonar Code Smells Metrics
Sonar Sqale Rating Metrics
Sonar Sqale Index Metrics
Sonar Ncloc Metrics
Reliability Sonar Reliability Rating Metrics
Security Sonar Security Rating Metrics
Sonar Vulnerabilities Metrics
Test coverage Sonar Coverage Metrics

feat(operator): pass validation options to constructor

briefcase Feature Request

1. User story

As an API consumer,
I need the option to ignore validOperators,
In order to extend Variable.

2. Acceptance criteria

We'll be done when:

  • 1. The Operator.constructor function accepts an options argument.
  • 2. The options argument has a throws: {boolean} property.

3. Notes

⌦ Provide additional information here, if you need to.

feat(variable): add StringVariable operators

briefcase Feature Request

1. User story

As a rule-base administrator,
I want to more operator options for StringVariables
In order to create and maintain succinct Rules and RuleSets.

2. Acceptance criteria

We'll be done when StringVariable provides these methods:

  • 1. endsWith determines whether a StringVariable.prototype.value ends with the characters of a specified StringVariable.prototype.value.
  • 2. hasMaxLength determines whether a single StringVariable.prototype.value is less than or equal to a specific character count (i.e., a NumberVariable.prototype.value).
  • 3. hasMinLength determines whether a single StringVariable.prototype.value is greater than or equal to a specific character count (i.e., a NumberVariable.prototype.value).
  • 4. isEmpty determines whether a single StringVariable.prototype.value has zero (0) characters (represented as a NumberVariable).
  • 5. isNotEmpty determines whether a single StringVariable.prototype.value has more than (0) characters (i.e., a NumberVariable.prototype.value of 0).
  • 6. isOneOf evaluates whether a StringVariable.prototype.value is an element in an ArrayVariable.prototype.value.
  • 7. includes determines whether one StringVariable.prototype.value may be found within another StringVariable.prototype.value.
  • 8. matches retrieves the result of matching a StringVariable.prototype.value against a regular expression.
  • 9. startsWith determines whether a StringVariable.prototype.value ends with the characters of another StringVariable.prototype.value.

3. Notes

  • As with all operators, these methods return a Proposition.
  • All methods include argument type checks, and will thrown an ArgumentError whenever given an unexpected type.

4. Attributions

These methods were inspired by Sindre Sorhus's external ow external module.

Sorhus, Sindre. (2019) StringPredicate | ow. Retrieved May 18, 2019, from https://sindresorhus.com/ow/classes/stringpredicate.html

defect: v1.1.0 package will not load

bug Defect Report

1. Summarize what you expected to happen

As an API consumer,
I must be able to require/import archetype-rules,
in order to use it.

2. Describe the defect (aka "bug")

Whenever one attempts to require the module, it throws an error:

const archetypesRules = require('[email protected]')
/* 
throws:
Error: Cannot find module './dist/archetypes-rules'
    at Function.Module._resolveFilename (internal/modules/cjs/loader.js:594:15)
    at Function.Module._load (internal/modules/cjs/loader.js:520:25)
    at Module.require (internal/modules/cjs/loader.js:650:17)
    at require (internal/modules/cjs/helpers.js:20:18)
*/

3. Acceptance criteria

When working properly, I expect that:

  • 1. The archetypes-rules module loads without error.
  • 2. All classes are available for use.

🐞 4. Steps to reproduce

View "defect: archetypes-rules v1.1.0 go to runkit" in RunKit to observe the error.

5. Your environment

⌦ Include as many relevant details about the environment in which the defect
occured.

⌦ Include as many relevant details about the environment in which the defect
occured.

  • archetypes-rules version: v1.1.0

  • JavaScript version (node --version): v10.5.0

  • npm version (npm --version): 6.9.0

  • Operating System and version (desktop or mobile):

    Hardware:

    Hardware Overview:
    
      Model Name: MacBook Pro
      Model Identifier: MacBookPro11,4
      Processor Name: Intel Core i7
      Processor Speed: 2.8 GHz
      Number of Processors: 1
      Total Number of Cores: 4
      L2 Cache (per Core): 256 KB
      L3 Cache: 6 MB
      Memory: 16 GB
      Boot ROM Version: 189.0.0.0.0
      SMC Version (system): 2.29f24
    

    Software:

    System Software Overview:
    
      System Version: macOS 10.12.6 (16G1918)
      Kernel Version: Darwin 16.7.0
      Time since boot: 35 days 11:10
    

docs(api): fully document public API

book Documentation Request

1. User story

As an API consumer,
I want to reference comprehensive API docs
In order to quickly use archetypes-rules.

2. Acceptance criteria

We'll be done when:

  • 1. All public-facing interfaces are correctly annotated with JSDoc3.
  • 2. We automatically generate and add all API documentation to each git commit.
  • 3. We publish the latest API documentation to GitHub Pages with each release.

3. Notes

⌦ Provide additional information here, if you need to.

refactoring: evaluate RuleElements with @sindresorhus/ow/isValid

code Refactoring proposal

1. Design summary / code smell(s)

Version 1.2.0 of archetypes-rules has:

  • 19 production dependencies
  • 62 development dependencies

2. Refactoring proposal(s)

  1. Simplify RuleContext evaluations with @sindresorhus/ow/isValid function.

  2. Rename the module @archetypes/rules.

  3. Extend all @archetypes/rules/Variables with @sindresorhus/ow methods (by ECMAScript data type).

3. Code quality improvement scores Sonar Quality Gate

  • The refactorings changes have either:

    • Reduced complexity, duplications, issues, security issues;
    • Improved maintainability or reliability; or
    • Both.

3.1. Complexity measures

These measures indicate how simple—or complicated—the control flow of the application is.
Cyclomatic Complexity
Measures the minimum number of test cases (i.e., conditional branches) are required for full test coverage.
Cognitive Complexity
Measures how difficult the application is to understand.
Version Cyclomatic Complexity Cognitive Complexity
v1.2.0 210 48
👎 v2.0.0 225 52

3.2. Source Lines Of Code (SLOC)

Version SLOC
v1.2.0 1,265
👎 v2.0.0 1,391

3.3. Dependencies (production)

Version Dependency count
v1.2.0 19
👍 v2.0.0 15

3.4. Bundle size (gzip)

Version Packed size Unpacked Size
v1.2.0 16.1 kB 68.9 kB
👎 v2.0.0 16.6 kB 71.2 kB

3.5. Code quality results summary

Measure Scores
Quality gate Sonar Alert Status Metrics
Defects (Bugs) Sonar Bugs Metrics
Duplications Sonar Duplicated Lines Density Metrics
Maintainability Sonar Code Smells Metrics
Sonar Sqale Rating Metrics
Sonar Sqale Index Metrics
Sonar Ncloc Metrics
Reliability Sonar Reliability Rating Metrics
Security Sonar Security Rating Metrics
Sonar Vulnerabilities Metrics
Test coverage Sonar Coverage Metrics

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.