Added ability to extend using modules

master
Mark Moffat 2020-01-03 18:51:24 +10:30
parent 2e5dfd576c
commit 5546341c1c
8 changed files with 62 additions and 40 deletions

View File

@ -200,11 +200,6 @@ payments and the sitemap for search engine indexing.
This email is used for any email receipts which are sent by your website.
##### Free shipping threshold
expressCart allows for the addition of a free shipping threshold. The cart will remove the shipping costs once the order has exceeded the `Free shipping threshold`
value. If the value of the cart is beneath the `Free shipping threshold`, the cart will add the `Flat shipping rate` to the total amount.
##### Payment Gateway
This determines which payment gateway to use. You will also need to configure your payment gateway configuration file here: `/config/<gateway_name>.json`
@ -321,6 +316,9 @@ The Instore config file is located: `/config/instore.json`. A example Instore se
```
Note: No payment is actually processed. The order will move to the `orderStatus` set and the payment is completed instore.
## Modules
It's possible to extend the basic functionality of `expressCart` using modules. All modules are loaded from `/lib/modules` at startup and added to the `config` for use throughout the app. There is an example module `shipping-basic` to calculate the flat shipping rate. One way to extend this basic module is to call a Postage service like [easypost](https://www.easypost.com/) to get an accurate rate for your location, package size etc.
## Email settings
You will need to configure your SMTP details for expressCart to send email receipts to your customers.

View File

@ -42,14 +42,6 @@
"type": "boolean",
"default": true
},
"flatShipping": {
"type": "number",
"default": 10
},
"freeShippingAmount": {
"type": "number",
"default": 100
},
"productsPerRow": {
"type": "number",
"default": 3
@ -114,6 +106,26 @@
"enableLanguages": {
"type": "boolean",
"default": true
},
"modules": {
"type": "object",
"properties": {
"enabled": {
"type": "object",
"properties": {
"shipping": {
"type": "string"
}
},
"required": ["shipping"]
}
},
"required": ["enabled"],
"default": {
"enabled": {
"shipping": "shipping-basic"
}
}
}
},
"required": [
@ -125,7 +137,8 @@
"emailPassword",
"emailAddress",
"paymentGateway",
"databaseConnectionString"
"databaseConnectionString",
"modules"
],
"additionalProperties": false
}

View File

@ -10,8 +10,6 @@
"emailPassword": "this_is_the_smtp_password",
"emailAddress": "hi@markmoffat.com",
"menuEnabled": true,
"flatShipping": 10,
"freeShippingAmount": 100,
"productsPerRow": 3,
"productsPerPage": 6,
"menuTitle": "Menu",
@ -25,5 +23,10 @@
"trackStock": false,
"orderHook": "",
"availableLanguages": ["en", "it"],
"defaultLocale": "en"
"defaultLocale": "en",
"modules": {
"enabled": {
"shipping": "shipping-basic"
}
}
}

View File

@ -131,9 +131,11 @@ const updateTotalCart = (req, res) => {
// Update the total items in cart for the badge
req.session.totalCartItems = Object.keys(req.session.cart).length;
// under the free shipping threshold
if(req.session.totalCartAmount < config.freeShippingAmount){
req.session.totalCartAmount = req.session.totalCartAmount + parseInt(config.flatShipping);
// Calculate shipping using the loaded module
const shippingCost = config.modules.loaded.shipping.calculateShipping(req.session.totalCartAmount);
if(shippingCost > 0){
req.session.totalCartShipping = parseInt(shippingCost);
req.session.totalCartAmount = req.session.totalCartAmount + parseInt(shippingCost);
req.session.shippingCostApplied = true;
}else{
req.session.shippingCostApplied = false;
@ -297,6 +299,19 @@ const getConfig = () => {
config.env = '';
}
// load modules
try{
config.modules.loaded = {};
Object.keys(config.modules.enabled).forEach((mod) => {
config.modules.loaded[mod] = require(`./modules/${config.modules.enabled[mod]}`);
});
}catch(ex){
console.log('Could not load modules, check your config.', ex);
process.exit(1);
}
console.log('config', config);
return config;
};
@ -369,10 +384,6 @@ const updateConfig = (fields) => {
settingsFile.flatShipping = parseInt(fields.flatShipping);
}
if(fields.freeShippingAmount){
settingsFile.freeShippingAmount = parseInt(fields.freeShippingAmount);
}
if(fields.productsPerRow){
settingsFile.productsPerRow = parseInt(fields.productsPerRow);
}

View File

@ -0,0 +1,13 @@
const shippingAmount = 10;
const freeThreshold = 100;
const calculateShipping = (amount) => {
if(amount >= freeThreshold){
return 0;
}
return shippingAmount;
};
module.exports = {
calculateShipping
};

View File

@ -107,9 +107,6 @@
"Cart URL": "Cart URL",
"This URL is used in sitemaps and when your customer returns from completing their payment.": "This URL is used in sitemaps and when your customer returns from completing their payment.",
"This is used as the \"from\" email when sending receipts to your customers.": "This is used as the \"from\" email when sending receipts to your customers.",
"Flat shipping rate": "Flat shipping rate",
"A flat shipping rate applied to all orders.": "A flat shipping rate applied to all orders.",
"Free shipping threshold": "Free shipping threshold",
"Orders over this value will mean the shipped will the FREE. Set to high value if you always want to charge shipping.": "Orders over this value will mean the shipped will the FREE. Set to high value if you always want to charge shipping.",
"Payment gateway": "Payment gateway",
"Payment_Gateway_Info": "You will also need to configure your payment gateway credentials in the `/config/&lt;gateway_name&gt;.json` file.",

View File

@ -109,9 +109,6 @@
"This URL is used in sitemaps and when your customer returns from completing their payment.": "Questo URL è usato nelle sitemaps e quando il tuo cliente ritorna per completare il suo pagamento",
"This is used as the \"from\" email when sending receipts to your customers.": "Questo è usato come \"from\" nelle email inviate ai clienti",
"Cart Email": "Cart Email",
"Flat shipping rate": "Tariffa di spedizione fissa",
"A flat shipping rate applied to all orders.": "Una tariffa di spedizione fissa da applicare a tutti gli ordini",
"Free shipping threshold": "Soglia di spedizione gratuita",
"Orders over this value will mean the shipped will the FREE. Set to high value if you always want to charge shipping.": "Ordini oltre questo valore avranno la spedizione GRATUITA. Configura un alto valore se vuoi sempre addebitare la spedizione.",
"Payment gateway": "Gateway pagamento",
"Payment_Gateway_Info": "Dovrai configurare anche le tue credenziali per il gateway di pagamento nel file `/config/&lt;gateway_name&gt;.json`.",

View File

@ -33,16 +33,6 @@
<input type="email" class="form-control" name="emailAddress" value="{{config.emailAddress}}" required>
<p class="help-block">{{ @root.__ "This is used as the \"from\" email when sending receipts to your customers." }}</p>
</div>
<div class="form-group">
<label>{{ @root.__ "Flat shipping rate" }} *</label>
<input type="text" class="form-control" name="flatShipping" value="{{config.flatShipping}}" required>
<p class="help-block">{{ @root.__ "A flat shipping rate applied to all orders." }}</p>
</div>
<div class="form-group">
<label>{{ @root.__ "Free shipping threshold" }}</label>
<input type="text" class="form-control" name="freeShippingAmount" value="{{config.freeShippingAmount}}">
<p class="help-block">{{ @root.__ "Orders over this value will mean the shipped will the FREE. Set to high value if you always want to charge shipping." }}</p>
</div>
<div class="form-group">
<label>{{ @root.__ "Payment gateway" }}</label>
<select class="form-control" name="paymentGateway">