Skip to content

Commit

Permalink
Add a new service plan providing service instances within a shared
Browse files Browse the repository at this point in the history
Matomo server.
  • Loading branch information
pdechamboux committed Oct 22, 2020
1 parent eb53e16 commit 1d6f1f4
Show file tree
Hide file tree
Showing 17 changed files with 336 additions and 112 deletions.
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ local.properties
.settings/
.loadpath
.factorypath
Servers/

# Locally stored "Eclipse launch configurations"
*.launch
Expand All @@ -47,3 +48,4 @@ local.properties
hs_err_pid*
headers
traces
*.bind.json
4 changes: 3 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ latest
`latest` specify that the latest stable release of Matomo has been selected, which corresponds to release file `matomo.zip`.

Then the default release can also be selected as follows:
* The file `default-release.txt` contains the release name that has been chosen:
* The file `default-release.txt` contains the release name that has been chosen. Example:
```
3.6.1
```
Expand Down Expand Up @@ -119,6 +119,7 @@ applications:
MATOMO-SERVICE_SMTP_CREDS: $SMTP_SERVICE_CREDS$
MATOMO-SERVICE_DOMAIN: $DOMAIN$
MATOMO-SERVICE_PHPBUILDPACK: $PHP_BUILPACK$
MATOMO-SERVICE_SHARED_CREDS: $SHARED_MYSQL_CREDS$
MATOMO-SERVICE_SHARED-DB_CREDS: $GLOBAL_SHARED_MYSQL_CREDS$
MATOMO-SERVICE_MATOMO-SHARED-DB_CREDS: $MATOMO_SHARED_MYSQL_CREDS$
MATOMO-SERVICE_DEDICATED-DB_CREDS: $DEDICATED_MYSQL_CREDS$
Expand All @@ -145,6 +146,7 @@ Change the file to fit your context by replacing all $...$ strings accordingly:
| $SMTP_SERVICE_CREDS$ | This is a column-separated string which mainly consists of the names of the credential fields in VCAP_SERVICES for the SMTP service to be bound to in order to send e-mails from Matomo instances | o-smtp:smtp-prod:host :port:username:password |
| $DOMAIN$ | The domain within which service instances are exposed | matomo.mycompany.com |
| $PHP_BUILDPACK$ | The PHP buildpack to be used to push Matomo instance to CF | php_buildpack |
| $SHARED_MYSQL_CREDS$ | This is a column-separated string which mainly consists of the names of the service and plan as well as the names of the credential fields in VCAP_SERVICES for the MySQL/MariaDB service to be bound to in order to store data for the shared Matomo instance for mutualized service instances | p-mysql:100MB:name:hostname :port:username:password |
| $GLOBAL_SHARED_MYSQL_CREDS$ | This is a column-separated string which mainly consists of the names of the service and plan as well as the names of the credential fields in VCAP_SERVICES for the MySQL/MariaDB service to be bound to in order to store data for Matomo instances within a globally shared DB | p-mysql:100MB:name:hostname :port:username:password |
| $MATOMO_SHARED_MYSQL_CREDS$ | This is a column-separated string which mainly consists of the names of the service and plan as well as the names of the credential fields in VCAP_SERVICES for the MySQL/MariaDB service to be bound to in order to store data for Matomo instances within a shared DB exclusively associated with Matomo service | p-mysql:1GB:name:hostname :port:username:password |
| $DEDICARED_MYSQL_CREDS$ | This is a column-separated string which mainly consists of the names of the credential fields in VCAP_SERVICES for the MySQL/MariaDB service to be bound to in order to store data for Matomo instances within a dedicated DB | ded-mysql:10GB:name:hostname :port:username:password |
Expand Down
1 change: 1 addition & 0 deletions manifest.yml
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ applications:
MATOMO-SERVICE_SMTP_CREDS: $SMTP_SERVICE_CREDS$
MATOMO-SERVICE_DOMAIN: $DOMAIN$
MATOMO-SERVICE_PHPBUILDPACK: $PHP_BUILPACK$
MATOMO-SERVICE_SHARED_CREDS: $SHARED_MYSQL_CREDS$
MATOMO-SERVICE_SHARED-DB_CREDS: $GLOBAL_SHARED_MYSQL_CREDS$
MATOMO-SERVICE_MATOMO-SHARED-DB_CREDS: $MATOMO_SHARED_MYSQL_CREDS$
MATOMO-SERVICE_DEDICATED-DB_CREDS: $DEDICATED_MYSQL_CREDS$
Expand Down
15 changes: 12 additions & 3 deletions src/main/doc/markdown/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,13 +13,16 @@ Note that the actual releases proposed by the service can be found [here](releas

Go to your CF marketplace and create a service instance by choosing among the proposed plans. There are three (only the first one is currently implemented, the two others are expected soon). Their objective is to provide different isolation levels in term of load and security of an instance, especially on the management of data (information from tracked Web sites):

1. global-shared-db
1. shared
All Matomo service instances are managed with many others (useful for dev purpose) within a unique Matomo server run in cluster mode within CloudFoundry.

2. global-shared-db
Data of all instances are stored in a database platform mutualized with many others (useful for dev purpose) within a unique schema. Matomo is run by one container (application instance) within CloudFoundry.

2. matomo-shared-db
3. matomo-shared-db
Data of this Matomo service instance is stored in a mutualized database platform with all other Matomo service instances of this kind (useful for tracked Web sites with small / medium traffic) but within dedicated schema. Matomo is run by a cluster of two containers and is configured to run in cluster mode.

3. dedicated-db
4. dedicated-db
Data of this Matomo service instance is stored in a dedicated database platform (useful for tracked Web sites with high traffic). Matomo is run by a cluster of at least two containers and is configured to run in cluster mode. It may scale up two a ten containers cluster as requested by the owner of the service instance.

Indeed, the choice among them depends on the traffic of the tracked Web site and has an impact on the cost of the service instance.
Expand Down Expand Up @@ -57,6 +60,8 @@ Version upgrade policy (see corresponding parameter name above) allows the creat

* `Explicit`: This policy gives complete control on release management of Matomo instances to its owner. This means that no upgrade of release may happen until explicitly requested by the instance owner. This can only be done by requesting an update of this instance (see section "Update instance").

Notice that no parameter can be specified for instances of the `shared` plan. They are always managed by the latest release available, which is automatically upgraded when a new one is published by the service.

While you have created a service instance, you can access it through the dashboard link associated to your instance. Indeed, to log into that Matomo instance, you need credentials. For that, you have to bind to that instance (see section "Bind to instances").

In case the creation of your instance has failed, you can delete it and retry. Even if an operation is frozen "in progress", it will fail after 30 minutes elapse time in this status. Then it will be finally possible to delete it in the end.
Expand Down Expand Up @@ -88,6 +93,10 @@ cf update-service ms -c '{"memorySize": 768}'
```
This number is forced to stay in the interval [256..2048]. This means that if a lower value than 256 is specified, then 256 is forced. In the same way, if a higher value than 2048 is specified, then 2048 is forced.

## The special case of the instance used for the "shared" plan

MCFS-SharedMatomoInstance

## Bind to instances

---
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,6 @@
import com.orange.oss.matomocfservice.web.service.ApplicationInformation;
import com.orange.oss.matomocfservice.web.service.InstanceIdMgr;
import com.orange.oss.matomocfservice.web.service.MatomoInstanceService;
import com.orange.oss.matomocfservice.web.service.MatomoReleases;
import com.orange.oss.matomocfservice.web.service.PlatformService;

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -124,7 +124,7 @@ public void initialize() {
LOGGER.debug("CONFIG::CloudFoundryMgr-initialize: SMTP service instance already exist");
smtpReady = true;
})
.subscribe();
.block();
// Check if global shared DB service has already been created and create otherwise
cfops.services().getInstance(GetServiceInstanceRequest.builder()
.name(properties.getDbCreds(ServiceCatalogConfiguration.PLANGLOBSHARDB_UUID).getInstanceServiceName(null))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Configuration;
import org.springframework.util.Assert;

import com.orange.oss.matomocfservice.servicebroker.ServiceCatalogConfiguration;

Expand All @@ -45,6 +46,7 @@ public class CloudFoundryMgrProperties {
private final static Logger LOGGER = LoggerFactory.getLogger(CloudFoundryMgrProperties.class);
private final static String SMTPINSTNAME = "mcfs-smtp";
final static String GLOBSHAREDDBINSTNAME = "mcfs-globshared-db";
final static String SHAREDDBUNKNOW = "unknown-shared-db";
private final static String SERVICESUFFIX = "-DB";
@Value("${matomo-service.matomo-debug:false}")
private boolean matomoDebug;
Expand All @@ -57,6 +59,8 @@ public class CloudFoundryMgrProperties {
private String servicePhpBuildpack;
@Value("${matomo-service.max-service-instances}")
private int maxServiceInstances;
@Value("${matomo-service.shared.creds}")
private String sharedCredsStr;
private DbCreds sharedCreds = null;
@Value("${matomo-service.shared-db.creds}")
private String sharedDbCredsStr;
Expand Down Expand Up @@ -116,7 +120,7 @@ public DbCreds getDbCreds(String planid) {
return this.dedicatedDbCreds;
} else if (planid.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
if (this.sharedCreds == null) {
this.sharedCreds = new DbCreds(null, null);
this.sharedCreds = new DbCreds(this.sharedCredsStr, SHAREDDBUNKNOW);
}
return this.sharedCreds;
}
Expand Down Expand Up @@ -180,36 +184,25 @@ public class DbCreds {
private String password;

DbCreds(String creds, String sharedServiceName) {
Assert.notNull(creds, "Should always provide a creds definition string");
this.sharedServiceName = sharedServiceName;
if (creds != null) {
String[] credsarr = creds.split(":");
this.service = credsarr[0];
this.plan = credsarr[1];
this.name = credsarr[2];
this.host = credsarr[3];
this.port = credsarr[4];
this.user = credsarr[5];
this.password = credsarr[6];
} else {
this.service = null;
this.plan = null;
this.name = null;
this.host = null;
this.port = null;
this.user = null;
this.password = null;
}
String[] credsarr = creds.split(":");
this.service = credsarr[0];
this.plan = credsarr[1];
this.name = credsarr[2];
this.host = credsarr[3];
this.port = credsarr[4];
this.user = credsarr[5];
this.password = credsarr[6];
}

public DbCreds addVars(Builder b) {
if (this.service != null) {
b.environmentVariable("MCFS_DBSRV", this.service);
b.environmentVariable("MCFS_DBNAME", this.name);
b.environmentVariable("MCFS_DBHOST", this.host);
b.environmentVariable("MCFS_DBPORT", this.port);
b.environmentVariable("MCFS_DBUSER", this.user);
b.environmentVariable("MCFS_DBPASSWD", this.password);
}
b.environmentVariable("MCFS_DBSRV", this.service);
b.environmentVariable("MCFS_DBNAME", this.name);
b.environmentVariable("MCFS_DBHOST", this.host);
b.environmentVariable("MCFS_DBPORT", this.port);
b.environmentVariable("MCFS_DBUSER", this.user);
b.environmentVariable("MCFS_DBPASSWD", this.password);
return this;
}

Expand All @@ -227,7 +220,7 @@ public boolean isDedicatedDb() {
}

public String getInstanceServiceName(String appName) {
if (sharedServiceName == null) {
if ((sharedServiceName == null) || (sharedServiceName.equals(SHAREDDBUNKNOW))) {
return appName + SERVICESUFFIX;
}
return this.sharedServiceName;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ public class PBinding extends POperationStatus {
@ManyToOne
@JoinColumn(name = "matomo_instance_id")
private final PMatomoInstance pmatomoInstance;

@Column(length = LENGTH_ID)
private final String appId;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.JoinColumn;
import javax.persistence.ManyToOne;
import javax.persistence.Table;

import org.springframework.cloud.servicebroker.model.instance.OperationState;
Expand Down Expand Up @@ -85,7 +87,11 @@ public class PMatomoInstance extends POperationStatus {

@Column(length = LENGTH_TIMEZONE)
private String timeZone;


@ManyToOne
@JoinColumn(name = "shared_matomo_instance_id")
private PMatomoInstance sharedInstance;

protected PMatomoInstance() {
super();
this.idUrl = -1;
Expand All @@ -104,6 +110,7 @@ protected PMatomoInstance() {
this.instances = 0;
this.memorySize = 0;
this.timeZone = null;
this.sharedInstance = null;
}

public PMatomoInstance(String uuid, int idUrl, String name, PlatformKind pfkind, String pfapi, String planid, PPlatform pf, Parameters mip) {
Expand All @@ -124,6 +131,20 @@ public PMatomoInstance(String uuid, int idUrl, String name, PlatformKind pfkind,
this.timeZone = mip.getTimeZone();
}

public PMatomoInstance(String uuid, int idUrl, String name, PlatformKind pfkind, String pfapi, String planid, PPlatform pf, Parameters mip, PMatomoInstance shared) {
this(uuid, idUrl, name, pfkind, pfapi, planid, pf, mip);
this.configFileContent = "fake_content".getBytes();
this.sharedInstance = shared;
}

public boolean isSharedPlan() {
return this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID);
}

public PMatomoInstance getSharedInstance() {
return this.sharedInstance;
}

public int getIdUrl() {
return this.idUrl;
}
Expand Down Expand Up @@ -152,6 +173,9 @@ public PlatformKind getPlatformKind() {
public String getPlatformApiLocation() {
return platformApiLocation;
}
public void setPlatformApiLocation(String api) {
this.platformApiLocation = api;
}

public String getPlanId() {
return this.planId;
Expand All @@ -173,77 +197,122 @@ public void setConfigFileContent(byte cfc[]) {
}

public boolean getAutomaticVersionUpgrade() {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return this.sharedInstance.getAutomaticVersionUpgrade();
}
return this.automaticVersionUpgrade;
}

public void setAutomaticVersionUpgrade(boolean avu) {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return;
}
this.automaticVersionUpgrade = avu;
super.touch();
}

public int getInstances() {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return this.sharedInstance.getInstances();
}
return this.instances;
}

public void setIntances(int instances) {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return;
}
this.instances = instances;
super.touch();
}

public int getMemorySize() {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return this.sharedInstance.getMemorySize();
}
return this.memorySize;
}

public void setMemorySize(int memorysize) {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return;
}
this.memorySize = memorysize;
super.touch();
}

public String getTimeZone() {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return this.sharedInstance.getTimeZone();
}
return this.timeZone;
}

public void setTimeZone(String timezone) {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return;
}
this.timeZone = timezone;
super.touch();
}

public void setInstalledVersion(String instVers) {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return;
}
this.installedVersion = instVers;
super.touch();
}

public String getInstalledVersion() {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return this.sharedInstance.getInstalledVersion();
}
return this.installedVersion;
}

public String getPassword() {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return null;
}
return this.password;
}

public void setDbCred(String dbc) {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return;
}
this.dbCred = dbc;
}

public String getDbCred() {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return null;
}
return this.dbCred;
}

public void setTokenAuth(String ta) {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return;
}
this.tokenAuth = ta;
}

public String getTokenAuth() {
if (this.planId.equals(ServiceCatalogConfiguration.PLANSHARED_UUID)) {
return this.sharedInstance.getTokenAuth();
}
return this.tokenAuth;
}

public Parameters getParameters() {
return new Parameters()
.version(this.installedVersion)
.autoVersionUpgrade(this.automaticVersionUpgrade)
.cfInstances(this.instances)
.memorySize(this.memorySize)
.timeZone(this.timeZone);
.version(getInstalledVersion())
.autoVersionUpgrade(getAutomaticVersionUpgrade())
.cfInstances(getInstances())
.memorySize(getMemorySize())
.timeZone(getTimeZone());
}

public enum PlatformKind {
Expand Down
Loading

0 comments on commit 1d6f1f4

Please sign in to comment.