Arteq Blog


Thursday, May 17th, 2012

Het maakt niet uit hoe veilig de infrastructuur is, vroeg of laat zal men de dupe zijn van een computer criminaliteit. Iemand kan een DDoS (Distributed Denial of Service) aanval loslaten op uw diensten, kan uw netwerk ‘sniffen’ of kan zelfs belangrijke informatie kopiëren of verwijderen. Het probleem van deze computercriminaliteit is dat men het vaak niet door heeft dat dit gebeurd. Dit kan echter voorkomen worden. Door een georganiseerd en beveiligd netwerk, kan men een melding krijgen wanneer er sprake is van computercriminaliteit. De eerste gedachte die bij mensen opkomt is dat ze de aanval direct moeten stoppen. Kosten wat het kost. Dit is echter niet de meest juiste beslissing. Indien men niet de juiste informatie in huis heeft, is het soms verstandig om het virus zijn gang te laten gaan en dit door een forensisch computer expert op laten lossen. In dit artikel zullen een aantal stappen besproken worden die door de expert genomen (kunnen) worden.

1. Het documenteren van het systeem
De naam, datum, tijd, doel, hardware, software, het is allemaal noodzakelijk dat dit gedocumenteerd wordt.

2. Verzamelen van bewijs
Alle informatie over de aanval dient voorzicht verwijderd te worden van het systeem. Dit wordt normaal gesproken gedaan door speciale software. Deze ‘hasht’ de informatie. Deze manier is legaal en kan het bewijs nog gebruikt worden. Het bewijs dat meestal wordt verzameld bestaat uit netwerk verbindingen, die nog actief zijn, processen die nog geladen worden in het geheugen en het bevat een kopie van alle informatie op de harde schijf. De volgende stap is het unpluggen of afsluiten van het geïnfecteerde systeem. Wanneer de log bestanden van het geïnfecteerde systeem elders zijn opgeslagen, dienen deze gekopieerd te worden. In Linux is het zo dat programma’s nog steeds uitgevoerd kunnen worden door middel van het commando: file /proc/[0-9]*/exe\grep “(deleted)”. Wanneer men een kopie wilt van deze lijst gebruikt men: /bin/dd if=/proc/filename/exe of=filename.

3. De tijdlijn (timeline) van de aanval reconstrueren
Als alle informatie gekopieerd is naar een beveiligd werkstation kan de timeline gereconstrueerd worden. Dit is een essentiële stap. Verander geen bestanden voordat de timeline gereconstrueerd is! De timeline slaat zien wanneer de bestanden voor het laatst zijn uitgevoerd, verwijderd en aangemaakt.

4. Diepgaande analyse van het geïnfecteerde systeem
Wanneer de informatie is verzameld, zal deze verder geanalyseerd worden. Het doel hiervan is het vinden van verdachte installaties, verwijderede of aangemaakte folders enzovoorts. Hiervoor zijn specifieke tools beschikbaar.

5. ‘File Information Restoration’
De niet toegewezen ruimte kan worden onderzocht om te kijken welke bestanden, nadat deze zijn samengevoegd, een tijd wordt weergegeven wanneer (bepaalde) bestanden zijn verwijderd. Dit kan van pas komen om de genomen stappen van de hacker te reconstrueren.

6. Zoeken
Maak gebruik van alle informatie om te zoeken naar een specifieke naam, IP adressen, bestandsnamen die kunnen leiden naar de indringer.

7. Rapporteren
Het maakt niet uit of het geinfecteerde systeem van bedrijf A of bedrijf B is, het is altijd verstandig om alle bevindingen te documenteren. Wanneer dit op de juiste manier gedaan wordt kunnen deze bevindingen gebruikt worden bij de rechtbank. Computer criminaliteit is geen grapje. Neem dit dus serieus! In dit digitale tijdperk zijn computer criminaliteiten net zo gevaarlijk als alle andere misdaden. Twijfel niet en schakel een specialist wanneer dit nodig is. Laat het budget het toe, richt dan een ‘Computer Security Incident Response Team’ op die zich bezig houdt met het onderzoeken naar computer criminaliteit en in kan grijpen wanneer dit nodig is.


Tuesday, May 15th, 2012

Amazon staat aan de top als Infrastructure as a Service (IaaS) provider met het Amazon Services (AWS) platform. Dit platform, waarop servers, netwerk services en meer, aangeboden on-demand, is ook bekend als cloud computing. AWS wordt door zowel kleine als grote bedrijven gebruikt om een schaakbord infrastructuur te bouwen, zonder dat er up-front kosten gemaakt worden. Er zijn veel services beschikbaar binnen AWS zoals servers, database, load balacing, storage enzovoorts.

Het monitoren van de ‘systeem health’ is een belangrijk onderdeel van iedere infrastructuur. Amazon voorziet in monitoring door middel van de CloudWatch service.

Amazon CloudWatch voorziet in AWS cloud resources monitoring en de plichtige klanten draaien op de AWS. Ontwikkelaars en systeem administators kunnen hier gebruik van maken om metrieken te verzamelen, inzicht te verkrijgen en ze kunnen direct reageren om de applicaties en de zaken draaiend te houden. Amazon CloudWatch monitort de AWS resources zoals Amazon EC2 en Amazon RDS DB gevallen en CloudWatch kan ook Custom metrics, die gegenereerd zijn door klantapplicaties en services. Met behulp van Amazon CloudWatch verkrijgt men zichtbaarheid op systeemniveau in resource benutting, applicatie performance en operationele health.

CloudWatch kan echter alleen services monitorendie gehost zijn binnen de Amazon Cloud. Dit is natuurlijk handig voor bedrijven die hun volledige Infrastructure hosten binnen Amazon, maar het is gebruikelijk voor AWS services dat ze slechts een klein gedeelte van de bedrijfsarchtectuur omvatten , met andere services die aangeboden worden door derivaten applicatie providers, die gehost worden in een lokaal data center of in eigen clouds draaien. Vooruitspoelt eerlijken is CloudWatch te beperkt. Er is dus een andere monitoring oplossing nodig. Voor dit probleem biedt Monitis een simpele en robuuste oplossing. Met behulp van Open  API kan Monitis metrics verzamelen afkomstig van diverse bronnen en presenteert dezelfde een eendrachtige, consistente manier, met vele mogelijkheden voor alerts en notificaties.

In dit artikel wordt er gekeken naar hoe CloudWatch monitoring geïntegreerd kan worden met een Monitis oplossing en er wordt een tool genoemd die deze integratie makkelijk maakt.

Monitis-CloudWatch Integratie

Monitis-CloudWatch zorgt voor de integratie van CloudWatch met Monitis. Deze applicatie geschreven in python is gebaseerd op het boot framework voor de interfacing van AWS API met de Monitis REST API. Monitis-CloudWatch ondersteunt momenteel vier AWS services namelijk Elastic Compute Cloud (EC2), Relational Database Service (RDS), Elastic Load Balancer (ELB) en Block Storge (EBS). Additionele AWS services zullen waarschijnlijk on de toekomst ondersteund worden.

Gebruik maken van Monitis-CloudWatch

De eerste stap om Monitis-CloudWatch te gebruiken is het het downloaden van de applicatie. De applicatie is verkrijgbaar via de Monitis Exchange Github opslagplaats. Deze kan ook geïnstalleerd worden net behulp van pip.

De installatie instructies gaan er van uit dat er een werkende python omgeving is, in combinatie met pip. Pip staat voor een python packagemaker manager. Instructies om python en een pip op te zetten zijn. Te vindenop http://pyhton.org/getit en http://www.pip-installer.org/en/lates t/installing.html.

Dit heeft als resultaat dat de SDK met de daarbij horende afhankelijkheden geïnstalleerde worden. Een tweede is dat de monitis_cloudwatch.py geïnstalleerd word waar later enkele voorbeelden van terug te vinden zijn.

API Keys

Om gebruik te kunne. Maken van Monitis-CloudWatch heeft men een API key nodig voor AmazonAWS en voor Monitis. De pAPI Key en de Secret Key zijn terug e vinden in de web applicatie van Monitis. (tools – API -API Key. Deze dienen toegevoegd te worden als omgeving variabelen. Voor Linux, OS X en andere Unix systemen werkt het iets anders. Men dient de Bash Shell uit te voeren en men plaatst het volgende .bashrc in de home Directory.

export MONITIS_APIKEY=REPLACE_THIS_WITH_YOUR_API_KEY
export MONITIS_SECRETKEY=REPLACE_THIS_WITH_YOUR_SECRET_KEY

De boot library die gebruikt wordt door Monitis-CloudWatch om toegang te krijgen tot de AWS maakt ook gebruik van omgevingsvariabelen. Deze zijn terug te vinden op de AWS accountagina. Ga naar Security Credentials onder de Access Keys tab. De Accesss Key en de Secret Access Key zijn belangrijk. Voeg deze keys hoe als omgevingsvariabelen om ze beschikbaar te maken voor boto. Dit geldt ook voor de Monitis Keys

export AWS_ACCESS_KEY_ID=REPLACE_THIS_WITH_YOUR_ACCESS_KEY_ID
export AWS_SECRET_ACCESS_KEY=REPLACE_THIS_WITH_YOUR_SECRET_ACCESS_KEY

Na de installatie van Monitis-CloudWatch

Nadat Monitis-CloudWatch is geïnstalleerd met de correcte sleutels is de volgende stap het verkrijgen van een catalogus van de huidige metrics. Iedere metric die verzameld wordt door CloudWatch kan ook gemanaged worden door Monitis-CloudWatch. Er kan een metric geselecteerd worden maar er kunnen ook meerdere metrics geselecteerd worden. Om deze catalogus te bekijken is er een argument nodig:

$ monitis_cloudwatch.py –catalog
AWS/ELB             lb-http-alpha                           HTTPCode_ELB_4XX
AWS/ELB             lb-http-alpha                           HealthyHostCount
AWS/ELB             lb-http-alpha                           UnHealthyHostCount
AWS/EC2             i-fe68629c                              CPUUtilization

Deze lijst is voor illustratieve doeleinden en om het beknopt te houden zijn er veel resultaten weggelaten. In dit voorbeeld wordt er een EC2 geval geselecteerd, namelijk i-fe68629c. Ook wordt de CPUUtilization metric geselecteerd. Wanneer men een metric uit de catalogus heeft geselecteerd moet deze geassocieerd worden met de Monitis monitor die aangemaakt is. Dit wordt één keer per metric gedaan.

$ monitis_cloudwatch.py –create –ec2 –instance i-bb1c7dde –metric CPUUtilization

Nadat de monitor is aangemaakt, verifieert men door middel ban de monitors weer te geven in een lijst om te kijken welke monitor is aangemaakt.

$ monitis_cloudwatch.py –list 3379  AWS/EC2 i-bb1c7dde.CPUUtilization

De volgende stap is het updaten van de monitor met de metrieke data.

$ monitis_cloudwatch.py  –ec2 –instance i-bb1c7dde –metric CPUUtilization \–update –from -4days –period 900

Bovenstaand commando maakt gebruik van een aantal argumenten die extra uitleg nodig hebben. Ten eerste, “-from-4days” geeft aan dat de query 4 dagen terug moet starten. Er is een corresponderende query, namelijk “-until” die het einde van de query tijd weergeeft. De standaard (default) waarde van -until is de huidige tijd. Indien “-from” is gespecificeerd, de default waarde een uur voorafgaand de huidige tijd is. De “-period” specificeert de granualiteit van de metrieke data die opgehaald is vanuit CloudWatch. Normaal gesproken worden er eens in de vijf minuten data opgehaald en opgeslagen door CloudWatch. Indien er een langere tijdsverloop wordt gespecificeerd, zal de data opgedeeld worden in groteren stukken. De periode is gedefinieerd in seconden dus als men kijkt naar het voorbeeld is 900 dus 15 minuten.

Andere opties

Er zijn nog een paar andere opties voor monitis_cloudwatch.py. Deze opties staan hier weergegeven.

Delete
De huidige monitors kunnen met behulp van delete worden verwijderd. De monitor dient Cher geïdentificeerd te worden door -id of -name.

$ monitis_cloudwatch.py –list 3379  AWS/EC2 i-bb1c7dde.CPUUtilization
$ monitis_cloudwatch.py –list –delete –name i-bb1c7dde.CPUUtilization
$ monitis_cloudwatch.py –list
$

Sandbox
Monitis levert ook een development sandbox voor ontwikkelaars die werkt op Custom monitors. Wanneer men werkt met de sandbox, voeg dan het -sandbox argument toe en voeg ook de volgende variabelen toe:

export MONITIS_SANDBOX_APIKEY=REPLACE_THIS_WITH_YOUR_API_KEY
export MONITIS_SANDBOX_SECRETKEY=REPLACE_THIS_WITH_YOUR_SECRET_K Y

Namespace
Er zijn vier argumenten die geselecteerd kunnen van de ondersteunende AWS namespaces. Deze worden gebruikt wanneer er monitors aangemaakt worden. Ze zorgen ervoor dat er gepaste CloudWatch queries gemaakt worden. Dit zijn de volgende argumenten: -ec2, -RDS, -ELB en -EBS.

Statistieken
CloudWatch rapporteert vijf verschillende metrieken. Dit zijn de metrieken Minimum, Maximum, Averag, Sum en SampleCount. Hierbij horen de volgende flags: -min, -max, -avg, -max, -sum, en -count.

Prefix (het voorvoegsel)
Soms is het handig om metrieken die aan elkaar gerelateerd zijn te groeperen. Hiervoor heeft Monitis-CloudWatch het prefix argument om een prefix (voorvoegsel) toe te voegen aan de gecreëerde monitors. Bijvoorbeeld:

$ monitis_cloudwatch.py –create –elb –prefix loadbalancers.production \–instance lb-http –metric RequestCount –sum
$ monitis_cloudwatch.py –update –elb –prefix loadbalancers.production \–instance lb-http –metric RequestCount –sum –from ‘-1 week midnight’ \ –until ‘today midnight’ –period 3600

De prefix wordt weergegeven in de grafiek die wordt weergegeven op www.monitits.com.

Monitis-CloudWatch in practice

Wanneer MCW in practice draait, kan de applicatie gebruikt worden om periodiek recente metrieken die afkomstig zijn vanaf Amazon AWS CloudWatch toe te voegen aan Monitis Custom monitors. Om verder te gaan met bovenstaand voorbeeld, wordt er een query gemaakt om het totaal RequestCount toe te voegen de Custom monitor. De eerste sap is het schrijven van een klein Shell script om de omgevingsvariabelen op te zetten en waarin monitis_cloudwatch.py

export AWS_ACCESS_KEY_ID=********************
export AWS_SECRET_ACCESS_KEY=****************************************
export MONITIS_SECRETKEY=**************************
export MONITIS_APIKEY=************************** /usr/local/bin/monitis_cloudwatch.py –update –elb –prefix loadbalancers.production \ –instance lb-http –metric RequestCount –sum –from ‘last hour’ –period 3600

Nu dit is geregeld, wordt er een taak aangemaakt die ieder uur draait.

0 * * * * sh $HOME/bin/http-lb-hourly.sh

Meerdere aanroepingen van monitis_cloudwatch.py kunnen toegevoegd worden aan het Shell script, om ervoor te zorgen dat er updates plaatsvinden vrije betrekking hebben op meerdere Custom monitors. Wordt de frequentie van de aak verhoogt heeft dit als resultaat dat er vaker updates plaatsvinden. Dit geeft specifiekere en betrouwbaardere resultaten.

Sunday, May 13th, 2012

In een voorgaand artikel (SQL Server 2008 overview), zijn de verschillende functies van Microsoft SQL Server opgesomd. In dit artikel ligt de focus op de laatste release van SQL Server, namelijk SQL Server 2012. Er zijn een aantal zaken toegevoegd, zoals de nieuwe ‘High Availability AlwaysOn, verbeterde security en de mogelijkheid om te synchroniseren met de cloud.

 

 

AlwaysOn bestaat uit twee hoofd componenten. Deze twee componenten zijn de ‘AlwaysOn Availability Groups’ en de ‘AlwaysOn Cluster Instances’. Een ‘availability group’ is een combinatie van databases die gehost worden op een primaire server en maximaal gehost worden op vier secundaire servers. Ieder lid van de groep is in staat om te reageren op client verzoeken indien de primaire groep niet beschikbaar is. Alle databases in de groep zijn aan elkaar gekoppeld (failover). Faalt er een database, wordt deze overgeplaats naar een andere datase. Deze functionaliteit is ingebouwd boven op de Windows Server Failover Clustering functionaliteit.

De hoge beschikbaarheid van de SQL server kan verbeterd worden door gebruik te maken van ‘Failover Cluster Instances’ (FCI). Deze aanpak vereist ‘share storage’, gedeelde opslag. Shared storage is niet vereist voor de AlwaysOn Availability Groups. De servers die in een ‘availability group’ zitten hebben alleen shared storage nodig als ze zich gedragen als een FCI.

Wees ervan bewust dat AlwaysOn availability groepen automatisch failover naar een andere replica hebben wanneer er een probleem met een primaire groep wordt gedetecteerd. Deze automatische failover wordt niet ondersteund in FCI, dus men moet zelf instellen  dat de availability group zich gedragen als FCI met handmatige failover.

Een andere service die Microsoft aanbied voor hoge beschikbaarheid van de SQL databases is SQL Azure Data Sync. SQL Azure Data Sync zorgt ervoor dat men op eenvoudige wijze de lokale SQL Server met de SQL Azure gegevens kan synchroniseren. Dit is de reden waarom SQL Server 2012 gezien wordt als een applicatie die klaar is voor de cloud. Dit heet ook wel een ‘cloud-ready application’. Er kan gekozen worden voor welke kolommen gesynchroniseerd moeten worden. Het is een volledige implementatie van een service en er hoeft geen extra code geschreven te worden om de synchronisatie plaats te laten vinden. Het kan gebruikt worden in combinatie met het ‘Disaster Recovery plan’ zodat men een complete kopie heeft van uw lokale database op een andere fysieke locatie. Hieronder staan een aantal nieuwe functionaliteiten van SQL Server 2012:

1)   Analysis Services

SQL Server 2012 biedt een uniform model voor alle behoeften van een organisatie. Dit is het ‘BI Semantic Model’. Het heeft de voordelen van tabellen en de multidimensionale modellen en het bevat het volgende: PowerPivot voor Excel om te voldoen aan de eisen van de eindgebruikers, PowerPivot voor Sharepoint om te voldoen aan de eisen die teams stellen en het bevat Analyses Services om te voldoen aan de eisen van een bedrijf. Er kan een keuze gemaakt worden tussen ‘chached’ en ‘passtrough storage mode’ en security op zowel rij- als celniveau.

2)   Reporting Services

Reporting Services zijn nu een SharePoint service die gebruik maakt van alle mogelijkheden die SharePoint bidet. Een grote verbetering heeft plaatsgevonden bij de alarmeringsfunctie voor de eindgebruikers. In SQL Server 2012 worden gebruikers gewaarschuwd als rapporten die voor hun belangrijk zijn veranderen. Dit wordt gedaan door middel van een gebruikersvriendelijke interface. Wat niet vergeten mag worden is dat het de Report Services in SQL Server 2012 Word en Excel 2007 en 2010 ondersteunen.

3)   Integration Services

Een van de nieuwe karakteristieken van de Intergration Services is het nieuwe Project model om te ontwikkelen. Het traditionele Package model wordt nog steeds ondersteund. Echter kan met behulp van het Project model gebruik gemaakt worden van geavanceerde functies, zoals: gecentraliseerd management van parameters en connection managers, het project kan automatisch beveiligd worden door middel van encryptie en alles is makkelijk beheersbaar.

Visual Studio voor Applications 3.0 en .NET 4.0 wordt ook ondersteund door SQL Server 2012 Integration Services.

SQL Server 2012 is in feite nog hetzelfde als SQL Server 2008 met de toevoeing van SQL Server 2012 Business Intelligence. Dit is een aangepaste versie van SQL Server die een platform biedt om business intelligence oplossingen te ontwikkelen op de meest veilige en schaalbare wijze. Alle functies die ondersteund worden in SQL Server 2012 kunnen hier gevonden worden en vergeleken worden.

 

Volg ons op Twitter:   

Wednesday, May 9th, 2012

De Monitis Java SDK biedt alle mogelijke manieren om een interne monitor agent te bouwen. Java geeft echter geen simpele manier om een custom monitor te bouwen. Door een paar simpele classes toe te voegen aan de reeds bestaande API is er een manier tot stand gekomen om op eenvoudige wijze een custom Java monitor, in feite iedere soort monitor, te bouwen. In dit artikel wordt beschreven wat er toegevoegd is aan de bestaande API en er wordt een voorbeeld gegeven.

 

Hoe de bestaande Java SDK van Monitis is verbeterd
Er zijn in feite twee classes toegevoegd:

  1. GenericCustomMonitorRunner.java
    Met behulp van deze class wordt er een nieuwe custom monitor toegevoegd aan de huidige scope van Monitis monitors.De noodzakelijke parameters en waarden zullen door de user class versterkt worden en het verlengt de IGenericCustomMonitor class.
  1. IGenericCustomMonitor.java
    Deze abstracte class biedt alle definities voor een ‘Generic Custom Monitor’. Gebruikers zullen hier gebruik van moeten maken om een (eigen) custom monitor te implementeren. (zie bijlage)

De corresponderende JAR file die aangemaakt is voor de nieuwe API werd gebruikt tijdens de tests. Gebruikers verstrekken slechts één simpele class en de gewenste monitor zal direct aangemaakt worden.

Het bouwen van de ‘Memcached Custom Monitor’
De ‘Memchached Custom Monitor’ is ontworpen met behulp van de manier die hierboven is beschreven. Deze monitor is alleen aangemaakt voor dit artikel zodat men screenshots toe kon voegen. Dit laat zien dat het aanmaken van een Custom Java Monitor erg simpel is.

Het testen van de ‘Custom Memchached Monitor’
De Memchached Custom Monitor is geactiveerd voor een test van 15 minuten en iedere minuut werd er data verzonden. De memchaced server werd belast (84 mes/sec rate voor het versturen en ontvangen van records) en draaide op een Linux Ubuntu 11.04. De machine waarop deze draaide was een Intel Pentium Dual Core 2.4GHz, 2GB RAM.

Om de resultaten te bekijken, voegt men een Custom Monitor widget toe aan uw Monitis account door middel van het Monitis menu: Manage Monitors à Custom Monitors. Selecteer daarna de custom monitor die is aangemaakt en klik op ‘Add to Window’. (zie bijlage)

Bijlages
Hieronder staat een screenshot afkomstig van de Monitis site:

Het is ook mogelijk om alle gemeten kolommen weer te geven in een grafiek.

Bovenstaande metingen laten zien dat de gemonitorde Memchaced server perfect werkt. Er is genoeg laadcapaciteit om op te lopen naar 160 verzoeken per minuut.

/**
 * Abstract class that provides definitions for Generic Custom Monitor.
 * User should extend it for implementing of own custom monitor
 */
public abstract class IGenericCustomMonitor {
         /**
          * For Monitis API calls you need API key.
          * To get your keys log in to your Monitis account
          *    go to Tools -> API -> API key
          *
          * get_apiKey() should keep and return your apiKey
          * @return - your apiKey
          */
         public String get_apiKey() {return null;}
         /**
          * For Monitis API calls you need Secret key.
          * To get your keys log in to your Monitis account
          *    go to Tools -> API -> API key
          *
          * get_secretKey() should keep and return your secretKey
          * @return - your apiKey
          */
         public String get_secretKey() {return null;}
         /**
          * @return - existing or new custom monitor name
          */
         public String get_monitor_name() {return null;}
         /**
          * @return - existing or new custom monitor tag value
          */
         public String get_monitor_tag_value() {return null;}
         /**
          * The duration interval between sending monitoring result
          *
          * @return processing time [ms]
          */
         public long get_processingTime() {return 60000;/*default - 1 min*/}
         /**
          * The duration for custom monitor test
          *
          * @return test duration [ms] (infinitely if returns <= 0)
          */
         public long get_testDuration() {return 300000;/*default - 5 min*/}
         /**
          * The new monitor can have some parameters
          *
          * Example for preparing  parameters
          * <pre>
          *       List<MonitorParameter> monitorParams =
new ArrayList<MonitorParameter>();
          *       monitorParams.add(new MonitorParameter("Quantity of servers",
"ServersNumber", "5", DataType.INTEGER, true));
          *       monitorParams.add(new MonitorParameter("password", "Password",
"mypass",
DataType.STRING, true))
          * </pre>
          *
          * @return - new custom monitor list of parameters
          * @see MonitorParameter class for details
          */
         public List<MonitorParameter> get_monitorParams() {return null;}
         /**
          * The resulting parameters should be defined for new custom monitor
          *
          * Example of preparing custom monitor result parameters
          * <pre>
          *       List<MonResultParameter> resultParams =
new ArrayList<MonResultParameter>();
          *       resultParams.add(new MonResultParameter("cpu", "CPU", "%", DataType.FLOAT));
          *       resultParams.add(new MonResultParameter("mem", "MEM", "MB", DataType.INTEGER));
          * </pre>
          *
          * @return - new custom monitor list of resulting parameters
          * @see MonitorParameter class for details
          */
         public List<MonResultParameter> get_resultParams() {return null;}
         /**
          * The current set of custom monitor results
          *
          * Example of generating custom monitor results
          * <pre>
          *       String cpu = String.format("%3.1f", (Min + (Math.random() * (Max - Min))));
          *       String mem = String.format("%2d", (int)(Min + (Math.random() * (Max - Min))));
          *       List<MonResult> results = new ArrayList<MonResult>();
          *       results.add(new MonResult("cpu", cpu));
          *       results.add(new MonResult("mem", mem));
          * </pre>
          *
          * @return custom monitor list of current results set
          * @see MonResult class for details
          */
         public List<MonResult> get_results() {return null;}
         /**
          * Monitor can be deleted after series of tests
          *
          * @return true if custom monitor have to be deleted after test
          */
         public boolean deleteMonitor() {return true;/* default value – delete monitor*/}
         /**
          * Test class will inform about ending test
          * by calling this method
          */
         public void signal_testEnded(int err_code){ }
}
public class MemcachedMonitor extends  IGenericCustomMonitor {
    private static final String apiKey = "4DURRI9JDEG5QN394DO14Q9C0D";
    private static final String secretKey = "1Q89OGT6BO95J4TH58A56S73T9";
    private static final String monitor_name = "Custom_monitor";//Name
    private static final String monitor_tag_value = "Memcached_monitor";//Monitor Group
    private static String servers = "localhost:11211";//local memcached server
    private static final long processingTime = 60;//default value - 60 sec (1 min)
    private static final long testDuration = 600;//default value - 600 sec (10 min)
    MemcachedClient cache = null;
    //storage of previous measured statistics
    Map<InetSocketAddress,Map<String,String>> stats_ = new HashMap<InetSocketAddress, Map<String, String>>();
    public MemcachedMonitor () throws Exception {
                 cache = buildMemcachedClient(servers);
    }
    private MemcachedClient buildMemcachedClient(String servers) throws Exception {
                 MemcachedClientBuilder builder = new XMemcachedClientBuilder(AddrUtil.getAddresses(servers));
                 builder.setCommandFactory(new BinaryCommandFactory());// use binary protocol
                 return builder.build();
    }
         public void signal_testEnded(int err_code){
                 System.exit(err_code);
         }
         public String get_apiKey() {
                 return apiKey;
         }
         public String get_secretKey() {
                 return secretKey;
         }
         public String get_monitor_name() {
                 return monitor_name;
         }
         public String get_monitor_tag_value() {
                 return monitor_tag_value;
         }
         public long get_processingTime() {
                 return processingTime * 1000;//ms
         }
         public long get_testDuration() {
                 return testDuration * 1000;//ms
         }
         public boolean deleteMonitor() {
                 return false;
         }
         public List<MonitorParameter> get_monitorParams() {
                 return null;
         }
         public List<MonResultParameter> get_resultParams() {
                 List<MonResultParameter> resultParams = new ArrayList<MonResultParameter>();
                 resultParams.add(new MonResultParameter("server", "server", "", DataType.STRING));
                 resultParams.add(new MonResultParameter("conns", "conns", "", DataType.INTEGER));
                 resultParams.add(new MonResultParameter("get_hits", "gets [per/s]", "", DataType.INTEGER));
                 resultParams.add(new MonResultParameter("get_misses", "misses [per/s]", "", DataType.INTEGER));
                 resultParams.add(new MonResultParameter("reqs", "reqs [per/s]", "", DataType.INTEGER));
                 resultParams.add(new MonResultParameter("hitratio", "hitratio [%]", "", DataType.FLOAT));
                 resultParams.add(new MonResultParameter("bytes", "usage [MB]", "MB", DataType.INTEGER));
                 resultParams.add(new MonResultParameter("usage", "usage [%]", "%", DataType.FLOAT));
                 resultParams.add(new MonResultParameter("curr_items", "items cached", "",
DataType.INTEGER));
                 resultParams.add(new MonResultParameter("bytes_read", "bytes read [per/s]", "", DataType.INTEGER));
                 resultParams.add(new MonResultParameter("bytes_written", "bytes written [per/s]", "", DataType.INTEGER));
                 resultParams.add(new MonResultParameter("evictions", "evictions [%]", "%",
DataType.FLOAT));
                 resultParams.add(new MonResultParameter("threads", "threads", "",
DataType.INTEGER));
                 return resultParams;
         }
         public List<MonResult> get_results() {
                 Map<InetSocketAddress,Map<String,String>> stats = null;
                 int curr_connections, curr_connections_;
                 int threads, threads_;
                 int curr_items, curr_items_;
                 long get_hits, get_hits_;
                 long get_misses, get_misses_;
                 long limit_maxbytes, limit_maxbytes_;
                 long bytes, bytes_;
                 long bytes_read, bytes_read_;
                 long bytes_written, bytes_written_;
                 long evictions, evictions_;
                 String res;
                 try {
                          stats = cache.getStats();// Get current statistics
                 }  catch (Exception e) {
                          e.printStackTrace();
                 }
        Iterator<InetSocketAddress> it = stats.keySet().iterator();
        StringBuffer buf = new StringBuffer();
          List<MonResult> results = new ArrayList<MonResult>();
        while (it.hasNext()) {
            SocketAddress s = it.next();
                          results.add(new MonResult("server", s.toString()));
            buf.append("\n---- Statistics for server ").append(s.toString()).append("\n");
            buf.append(TimeUtility.format(TimeUtility.getNowByGMT().getTime(), "yyyy-MM-dd HH:mm:ss"));
            //Current results
            Map<String, String> stat = stats.get(s);
            curr_connections = Integer.parseInt(stat.get("curr_connections")); /*Number of open
connections*/
            threads = Integer.parseInt(stat.get("threads")); /*Number of worker threads requested*/
            get_hits = Long.parseLong(stat.get("get_hits")); /*Number of keys that have been
requested and found present*/
            get_misses = Long.parseLong(stat.get("get_misses")); /*Number of items that have been requested and not found*/
            limit_maxbytes = Long.parseLong(stat.get("limit_maxbytes")); /*Number of bytes this
server is allowed to use for storage*/
            bytes = Long.parseLong(stat.get("bytes")); /*Current number of bytes used to store items*/
            curr_items = Integer.parseInt(stat.get("curr_items")); /*Current number of items
stored*/
            bytes_read = Long.parseLong(stat.get("bytes_read"));/*Total number of bytes read
by this server from network*/
            bytes_written = Long.parseLong(stat.get("bytes_written"));/*Total number of bytes
sent by this server to network*/
            evictions = Long.parseLong(stat.get("evictions"));/*Number of valid items removed
from cache to free memory for new items*/
            //previous results
            if (stats_.size() <= 0) {
                          curr_connections_ = threads_ = curr_items_ = 0;
                          get_hits_ = get_misses_ = limit_maxbytes_ = bytes_ = bytes_read_ = bytes_written_ = evictions_ = 0;
            } else {
                Map<String, String> stat_ = stats_.get(s);
                curr_connections_ = Integer.parseInt(stat_.get("curr_connections")); /*Number of open connections*/
                threads_ = Integer.parseInt(stat_.get("threads")); /*Number of worker threads
requested*/
                get_hits_ = Long.parseLong(stat_.get("get_hits")); /*Number of keys that have been requested and found present*/
                get_misses_ = Long.parseLong(stat_.get("get_misses")); /*Number of items that
have been requested and not found*/
                limit_maxbytes_ = Long.parseLong(stat_.get("limit_maxbytes")); /*Number of bytes this server is allowed to use for storage*/
                bytes_ = Long.parseLong(stat_.get("bytes")); /*Current number of bytes used to
store items*/
                curr_items_ = Integer.parseInt(stat_.get("curr_items")); /*Current number of items stored*/
                bytes_read_ = Long.parseLong(stat_.get("bytes_read"));/*Total number of bytes
read by this server from network*/
                bytes_written_ = Long.parseLong(stat_.get("bytes_written"));/*Total number of bytes sent by this server to network*/
                evictions_ = Long.parseLong(stat_.get("evictions"));/*Number of valid items
removed from cache to free memory for new items*/
            }
            //Number of open connections
                results.add(new MonResult("conns", String.valueOf(curr_connections)));
                buf.append("\tconns: ").append(String.valueOf(curr_connections));
                //Number of keys that have been requested and found present per sec.
                res = String.valueOf((get_hits - get_hits_) / processingTime);
                results.add(new MonResult("get_hits", res));
                buf.append("\tget_hits: ").append(res);
                //Number of items that have been requested and not found per sec.
                res = String.valueOf((get_misses - get_misses_) / processingTime);
                results.add(new MonResult("get_misses", res));
                buf.append("\tget_misses: ").append(res);
                //Total number of keys that have been requested per sec.
                res = String.valueOf(((get_hits +  get_misses)-(get_hits_ +  get_misses_)) /
processingTime);
                results.add(new MonResult("reqs", res));
                buf.append("\treqs: ").append(res);
                //Percent of number of keys that have been requested and found present to total
number of keys that have been requested
                res = String.format("%3.1f", (get_hits < 1?1: get_hits)  * 100.0 / ((get_hits +  get_misses) < 1? 1:(get_hits +  get_misses)));
                results.add(new MonResult("hitratio", res));
                buf.append("\thitratio: ").append(res);
                //Current number of bytes used to store items [MB]
                res = String.format("%5.1f", bytes / 1024.0/1024.0);
                results.add(new MonResult("bytes", res));
                buf.append("\tbytes: ").append(res);
                // Storage usage in percents
                res = String.format("%3.1f", (bytes * 100.0) / limit_maxbytes);
                results.add(new MonResult("usage", res));
                buf.append("\tusage: ").append(res);
                //Current number of items stored
                results.add(new MonResult("curr_items", String.valueOf(curr_items)));
                buf.append("\tcurr_items: ").append(String.valueOf(curr_items));
                //Total number of bytes read by this server from network per sec.
                res = String.valueOf((bytes_read - bytes_read_) / processingTime);
                results.add(new MonResult("bytes_read", res));
                buf.append("\tbytes_read: ").append(res);
                //Total number of bytes sent by this server to network per sec.
                res = String.valueOf((bytes_written - bytes_written_) / processingTime);
                results.add(new MonResult("bytes_written", res));
                buf.append("\tbytes_written: ").append(res);
                // Percent of valid items removed from cache to free memory to current number of items stored
                res = String.format("%3.1f", evictions * 100.0 / (curr_items < 1?1:curr_items));
                results.add(new MonResult("evictions", res));
                buf.append("\tevictions: ").append(res);
                //Number of worker threads requested
                results.add(new MonResult("threads", String.valueOf(threads)));
                buf.append("\tthreads: ").append(String.valueOf(threads));
        }
        System.out.println(buf.toString());
        stats_.putAll(stats);
          return results;
         }
         public static void main(String[] args) {
                 try {
                          GenericCustomMonitorRunner tst = new GenericCustomMonitorRunner(new
MemcachedMonitor());
                 } catch (Exception e) {
                          System.err.println("Exception while test custom monitor: "+ e.getMessage());
                          System.exit(0);
                 }
         }
}

Sunday, May 6th, 2012

Het internet is een geweldige bron, maar soms kost het teveel tijd en energie om door honderden webpagina’s te zoeken naar tips over het gebruik van Tomcat met een database. Monitis heeft een aantal tips op een rijtje gezet om het leven weer wat makkelijker te maken! In dit artikel worden een aantal tips beschreven, afkomstig van het internet.

 

Tip #1 – Negeer de Database Performance niet
Webapps maken negen van de tien keer gebruik van databases. De webapp dient daarom afgestemd te worden met de database om een optimale performance te verkrijgen. Performance test de database en definieert een adequate database connection pool (maxActive, maxIdle, MaxWait, enzovoorts)

Tip #2 – Stel de oorzaak van de Database Connection Timeouts vast
Het simpelweg verhogen van de MaxWait in het resource-element is niet de beste manier om database connection timeouts te verhelpen. De timeouts kunnen namelijk het resultaat zijn van de ‘garbage collection’.
Garbage collection vereist dat alle processen die draaien op de virtuele Java machine tijdelijk stoppen met draaien. Als dit proces te veel tijd in beslag neemt, slaat de database connection op time out. De time out is dus niet ontstaan door een probleem in de applicatie, maar de time out is ontstaan doordat de Gabage Collection teveel tijd in beslag neemt.

Hoe vaker er Garbage Collection plaatsvindt, hoe minder garbage er per keer wordt verzameld. Hierdoor heeft het proces minder tijd nodig. Configureer dit zodat dit proces niet langer dan één seconde duurt.

Tip #3 – Deel Database Connection
Als iedere applicatie de database connectie opent en ook weer sluit, draaien alle applicaties langzamer. Door database connecties te delen met de applicaties en deze terug te laten keren naar een gemeenschappelijke ‘pool’, draaien de applicaties sneller.

Tomcat kan zo geconfigureerd worden dat er sprake is van ‘connection pooling’. Wijzig de waarden van maxActive en maxIdle in de bron van het element en de klus is geklaard.

Tip #4 – Zorg ervoor dat de Database Connection op de juiste manier terug komen in de ‘pool’
Sluit de databaseverbindingen niet twee keer. Wanneer men gebruik maakt van connection pooling, sluit men de database de eerste keer zodat die terugkeert naar de connection pool. De tweede keer dat de database wordt gesloten, kan het voorkomen dat men perongeluk de verbinding verbreekt nadat een andere applicatie gebruik gaat maken van de verbinding. Als er geexperimenteerd wordt men ‘Connection Closed’ uitzonderingen, kan dit de oorzaak zijn. Doe dit daarom niet!

Tip #5 – Configureer de database als een Global Naming Resource of ‘For a Single Context’
Identificeer de Java Database Connectivity (JDBC) database in een resource element in het context.xml bestand, indien men wilt dat de resource beschikbaar is voor één specifieke applicatie. Identificeer de JDBC resource in een resource element in het server.xml bestand indien men wilt dat de resource beschikbaar moet zijn voor alle applicaties.

Als er meerdere applicaties toegang nodig hebben tot een database, kan de database resource globaal aangemaakt worden in het server.xml bestand. Een andere mogelijkheid is dat iedere applicatie zijn eigen resource aanmaakt in een eigen context.xml bestand. De gebruiker beslist zelf wat de beste manier is.

Het beschikbaar stellen van databases voor één specifieke applicatie (in het context.xml bestand) heeft als resultaat dat de resource aangemaakt wordt wanneer de applicatie start. Databases globaal beschikbaar stellen (in het server.xml bestand) zorgt ervoor dat de resource aangemaakt wordt wanneer de server start. Wanneer de server herstart wordt, moet men ook de resource configuratie aanpassen.
Het configureren van de database resource in het context.xml bestand wordt aangeraden omdat dit ervoor zorgt dat de applicatie portable is.

Indien verschillende applicaties verschillende toegangsniveaus hebben en deze toegangsniveaus bepaald zijn met behulp van het database user ID, dan moet de database resource ook in ieder context.xml bestand van de applicaties geconfigureerd worden.

Tip #6 – Configureer de database als een Global Naming Resource of ‘For a Single Context’
De JDBC-ODBC (Open Database Connectivity) Bridge gecombineerd met de Java Delevopment Kit (JKD) van Tomcat was nooit bedoeld voor een productie omgeving. Het moet echter gebruikt worden als een ‘third-party driver’.Tomcat gebruiken in combinatie met een database is simpel. Het enige wat men nodig heeft zijn een aantal goede tips die ervoor zorgen dat de database performance geen problemen ondervindt. Monitis deelt graag deze kennis en geeft graag advies.

 

Volg ons op Twitter:   

Thursday, May 3rd, 2012

Nasuni heeft nieuwe testresultaten vrijgegeven waaruit blijkt dat het tien keer zo lang duurt om grote hoeveelheden data op te slaan in de ‘Amazone storage cloud’ dan op te halen in vergelijking met de concurrenten Windows Azure en Rackspace.

Volgens een recent verhaal afkomstig van de ‘ars technica blog Uptime’ heeft Nasuni vijf testen uitgevoerd. Bij iedere test werd 12TB data verplaats tussen twee cloud services. Het verplaatsen van 12TB data van de ‘Amazone Simple Storage Service (S3) naar Azure neemt 40 uur in beslag, terwijl het verplaatsen van dezelfde hoeveelheid data van Azure naar Amazon slechts 4 uur in beslag neemt.

Waarom is er zo’n groot verschil in snelheid wanneer er data verplaats wordt?

Nasuni zei dat de ‘grootste beperkende factor’ het schrijfvermogen van de cloud is, aangezien alle transfers naar Amazon S3 tussen de vier en vijf uur in beslag namen, terwijl het schrijven naar Microsoft Windows Azure en Rackspace veel minder tijd in beslag nam. Hieronder staan een aantal andere resultaten afkomstig uit de studies van Nasuni:

  • Rackspace naar Amazon nam 5 uur in beslag
  • Amazon naar Rackspace nam bijna een week tijd in beslag
  • Tussen Amazon ‘buckets’ nam 4 uur in beslag

De testresultaten varieerden door het moment van de dag en het aantal ‘compute machines’ (computers etc.) om de gegevens over te brengen. Deze resultaten geven echter de minimale tijd die nodig is om 12TB te verplaatsen.

Wil je weten hoe jou cloud platform presteert? Probeer de monitoring van Monitis voor cloud services. Met behulp van de Monitis Cloud Monitor kan men het aantal actieve exemplaren en de geinstalleerde software monitoren, in combinatie met andere parameters. Het zorgt er ook voor dat ‘configuration management’ van de grote aantallen servers in de cloud makkelijker is.

Volg ons op Twitter:   

Wednesday, May 2nd, 2012

In dit artikel zal het ‘boxing & unboxing’ principe besproken worden. Dit artikel is deel van een reeks artikelen die betrekking hebben op het optimaliseren van .NET code. Wat is ‘Boxing & Unboxing’? Bepaalde waarde typen, ook wel value types, kunnen geconverteerd worden naar referentie types, ook wel reference types. Wanneer een value type variabele geconverteerd moet worden naar een reference type, wordt er een object (een box) toegewezen aan de hoop om de waarde (value) vast te houden en wordt de value gekopieerd in de box. Dit noemt men ‘Boxing’. Boxing kan impliciet of expliciteit zijn. Dit is terug te zien in onderstaande code:

int p = 123; Object box; box = p;            // Impliciete boxing box = (Object)p;    // Expliciete boxing met een ‘cast’

Boxing komt meestal voor bij het passeren van een value type naar een methode die een object als parameter gebruikt. Wanneer een value in een object geconverteerd wordt in een value type en de value gekopieerd wordt uit de box naar een bepaalde locatie waar deze wordt opgeslagen, noemt men dit ‘unboxing’.

p= (int)box; // Expliciete boxing met een ‘cast’

Problemen die zich voor doen bij het boxen worden verergerd door het gebruik lussen (ook wel loops) of wanneer een grote hoeveelheid data opgeslagen wordt als value types.

Vermijd frequente ‘Boxing en Unboxing Overhead’
Boxing veroorzaakt een hoop toewijzingen en zorgt voor het kopiëren van geheugen. Om het boxen tegen te gaan moet men value types niet zien als reference types. Vermijd ook het doorgeven van value types in methode types die gebruik maken van een reference type. Indien boxing onvermijdbaar is, is het aan te raden om de variabele één keer te boxen en een object reference gekopieerd te houden in de box zo lang dit nodig is. Wanneer men het value type nodig heeft kan dit unboxed worden. Dit zorgt ervoor dat de overhead laag blijft.

int p = 123; object box; box = (object)p;    // Explicit boxing met een 'cast'  // Gebruik de box variabele in plaats van p

Verzamelingen (collections) en ‘Boxing’
Collections slaan alleen data op die als basis type Object zijn. Het doorgeven van value types zoals integers en kommagetallen aan collections zorgt ervoor dat er boxing plaatsvindt. Een veelvoorkomend scenario is het vullen van collections met int en float type gegevens vanuit een database. Dit kan ernstige overhead veroorzaken bij collections door iteratie. Hieronder staat een voorbeeld:

ArrayList al = new ArrayList (); for (int i = 0; i <1000; i + +) al.Add (i)                 // Impliciet boxed, omdat Voeg () neemt een object int f = (int) al [0];             // Het element is unboxed

Om dit te voorkomen dient men gebruik te maken van een array. Een andere mogelijkheid is om een collection class aan te maken voor het specifieke value type. Unboxing moet met een expliciete ‘cast operator’ worden uitgevoerd.

Het meten van ‘Boxing Overhead’
Er zijn meerdere manieren om de ‘Boxing Overhead’ te meten. Men kan gebruik maken van de ‘Performance Monitor’ om de prestatie impact van boxing overhead op de benutting van de resources en op de response tijden van de applicatie te meten. Om een statische analyse te doen, kan de MSIL code geanalyseerd worden. Dit geeft een exact beeld van waar men geaffecteerd is door boxing en unboxing. Dit doet men door in de code te zoeken naar box en unbox instructies in de MSIL code.  Onderstaand commando wordt hiervoor gebruikt:

Ildasm.exe yourcomponent.dll /text | findstr box
Ildasm.exe yourcomponent.dll /text | findstr unbox

Echter dien je op te letten waar je de boxing overhead optimaliseert. De overhead is significant op plaatsen waar frequentie iteraties zoals loops, invoeringen en ontvangen van data value types in collections plaatsvinden.  Op plekken waar boxing slechts één of twee keer voorkomt is het niet de moeite waard om de boxing te optimaliseren.

Gebruik DirectCast in Visual Basic .NET
Maak, in plaats van CType, gebruik van DirectCast om door de hiërarchie heen te lopen. DirectCast compileert het direct in MSIL. Een kanttekening is dat DirectCast een InvalidCastException tussen twee variabelen zet indien er geen erfelijke relatie tussen de twee types aanwezig is.

 

Volg ons op Twitter: 

Sunday, April 29th, 2012

Dit artikel gaat over het managen en monitoren van SharePoint. In een voorgaand artikel zijn een aantal SharePoint ‘basic systeem performance counters’ aan bod gekomen waarmee men de ‘gezondheid’ van de server kan monitoren waar SharePoint op draait. Dit is een vereiste voordat men SharePoint op een effectieve manier kan monitoren. Door SharePoint te monitoren kan men mogelijke bottlenecks detecteren. Verder worden er in dit artikel ook een aantal best practices besproken worden.

SharePoint 2010 biedt een aantal ingebouwde monitoring mogelijkheden om problemen te diagnosen en om de performance te monitoren. Diagnostische monitoring is standaard ingeschakeld. Deze standaard monitoring is meestal voldoende, maar het kan zijn dat men deze instellingen wilt wijzigen. Stel er een grote verandering van de omgeving plaatsvindt, dan kunnen de instellingen gewijzigd worden. Deze instellingen kunnen zo aangepast worden, dat er uitgebreidere monitoring plaatsvindt. Dit schept meer inzicht en men krijgt een specifieker beeld van de SharePoint.

Naast de registratie van diagnostische gegevens, maakt SharePoint gebruik van zogenaamde geplande taken betreft de monitoring van gegevens met betrekking tot de  ‘health’ en het gebruik van de omgeving. De verzamelde gegevens bevatten performance counters, ‘event log data’,  ‘Web analysis rapporten’ en administratieve rapporten. Dit schema kan aangepast worden waardoor men zelf kan bepalen of er minder of juist meer gegevens verzameld moeten worden. Onderstaande tabel geeft alle instellingen (settings) weer, die helpen om de performance counters en andere instellingen te wijzigen.

Setting Waarde Opmerkingen
Event Log Flooding Protection Uitgeschakeld De standaard waarde is ‘Ingeschakeld’. Het kan uitgeschakeld worden om zo veel mogelijk data te monitoren als mogelijk is. Voor normaal gebruik dient deze ‘Ingeschakeld’ te zijn.
Timer Job Schedule    
Microsoft SharePoint Foundation Usage Data Import 5 minuten De standaard waarde is 30 minuten. Het verlagen van deze waarde zorgt ervoor dat de data vaker in de database wordt geïmporteerd. Dit is handig voor het oplossen van problemen. Voor normaal gebruik dient deze waarde 30 minuten te zijn.

 

Diagnostic Providers    
Enable all diagnostic providers Ingeschakeld Standaard: ‘Uitgeschakeld’, met uitzondering van  ‘Search Health Monitoring – Trace Events’ provider. Deze providers verzamelen ‘health’ data van verschillende functies en componenten.  Voor normaal gebruik dient deze uitgeschakeld te zijn.
Set “job-diagnostics-performance-counter-wfe-provider” and “job-diagnostics-performance-counter-sql-provider” Schedule Intervals 1 minuut Standaard waarde is 5 minuten. Het verlagen van deze instelling zorgt er voor dat de data vaker gemonitord kan worden. Dit is handig voor het oplossen van fouten. Voor normaal gebruik dient deze op 5 minuten te staan.
Miscellaneous    
Enable stack tracing for content requests Ingeschakeld Standaard: ‘Uitgeschakeld’. Het inschakelen zorgt ervoor dat foutmeldingen gebruik maken van de ‘process stack trace’. Voor normaal gebruik dient deze waarde uitgeschakeld te zijn.
Enable the Developer Dashboard Ingeschakeld Standaard: ‘Uitgeschakeld’. Het inschakelen zorgt ervoor dat de diagnoses van langzame pagina’s en ander problemen gebruik maken van het ‘Developer Dashboard’. Voor normaal gebruik (als er geen problemen meer zijn) dient deze waarde uitgeschakeld te zijn.
Usage Data Collection    
Content Import UsageContent Export UsagePage RequestsFeature Use

Search Query Use Site Inventory Usage Timer Jobs Rating Usage

Ingeschakeld Het inschakelen van deze waarde zorgt ervoor dat deze counters meer verbruik-data verzameld worden. Dit geeft inzicht in het ‘traffic’ (verkeer) van de omgeving.

Performance Counters
Men kan ‘performance counters’ die hieronder staan weergegeven toevoegen als er gebruik gemaakt wordt van de gebruikers-database. Deze counters zijn automatisch ingelogd en hebben een standaard interval van 30 minuten. Performance counters worden met behulp van de PowerShell cmd Add-SPDiagnosticsPerformanceCounter toegevoegd. Als bijvoorbeeld de Processor Tijd counter toegevoegd moet worden, doet men dit met behulp van het volgende commando:

Add-SPDiagnosticsPerformanceCounter -Category “Processor” -Counter “% Processor Time” -Instance “_Total” –WebFrontEnd

Dit commando hoeft maar op één van de Web server toegepast te worden, indien met meerdere Web servers in de SharePoint omgeving heeft. Onderstaande tabel geeft de counters weer die toegevoegd kunnen worden met behulp van het commando:

Add-SPDiagnosticsPerformanceCounter 

System
Counters
Omschrijving
% Processor Time Laat het gebruik over een bepaalde periode zien. Indien deze regelmatig te hoog is, kan men opmerken dat de performance geaffecteerd is. Het is belangrijk dat men het ‘Totaal’ telt in multiprocessor sytemen. Om een gebalanceerd systeem te krijgen, meet men ook alle processesors individueel.

 

Disk  
- Avg. Disk Queue Length Deze laat het gemiddelde ‘read and write’ verzoeken die ‘queued’ zijn vanaf de geselecteerde schijf gedurende het interval. Een grotere schijf wilt niet zeggen dat dit problemen geeft, maar het is belangrijk dat men dit goed monitord.

 

Avg. Disk Read Queue Length Het gemiddelde van het aantal lees verzoeken die in de wachtrij zijn geplaatst.

 

 

Avg. Disk Write Queue Length Het gemiddelde van het aantal schrijf verzoeken die in de wachtrij zijn geplaatst.
Disk Reads/sec Het aantal lezingen vanaf de schijf per seconde.
Disk Writes/sec Het aantal schrijvingen naar de schijf per seconde.

 

Memory  
- Available Mbytes Geeft het beschikbaar fysieke geheugen per locatie weer. Onvoldoende geheugen zorgt ervoor dat het aantal pagina fouten oploopt.
- Cache Faults/sec Geeft het aantal fouten weer van wanneer een pagina gezocht wordt in het system chache en niet gevonden kan worden. Het kan een klein foutje zijn wanneer het bestand niet gevonden kan worden in het geheugen omdat het op de schijf staat. Het juiste gebruik hiervan zorgt voor verhoogde server performance. Men moet verhoogde ‘cache failures’ monitoren, aangegeven door een verlaging in het Async Fast Reads/sec of Read Aheads/sec.

 

- Pages/sec Geeft het aantal pagina’s die gelezen of geschreven worden naar de schijf om pagina fouten op te lossen. Indien deze waarde stijgt, zijn er problemen met het hele systeem prestaties.
Paging File  
- % Used and % Used Peak De ‘server paging file’ wordt soms ook ‘swap file’ genoemd. Dit geeft de ‘virtuele’ geheugen adressen op de schijf weer. Als er een proces stopt komt deze fout naar boven en wanneer de ‘virtuele’ bronnen vanuit de schijf naar het geheugen gebruikt worden.

 

NIC  
- Total Bytes/sec De snelheid waarmee data is verzonden en ontvangen via de network interface card. Uitgebreid onderzoek is vereist waneer dit hoger is dan 40-50 procent dan de netwerk capaciteit is.
Process  
- Working Set Geeft de hoeveelheid (in bytes) van de werkende set weer. Dit geheugen is gereserveerd voor het process, ook al wordt dit niet gebruikt.
- % Processor Time Deze counter geeft het percentage van de processtijd die gebruikt wordt door een process weer.
Thread Count (_Total) Het huidige nummer van lijnen (threads).

 

 

ASP.NET  
Requests Total Het totale aantal aanvragen sinds het starten van de service.

 

Requests Queued Deze counter laat het aantal verzoeken die nog uitgevoerd moeten worden zien.
Request Wait Time Geeft het aantal milliseconden van de meest recente verzoeken die in de wachtrij staan weer. Het verhogen van dit nummer houdt in dat gebruiker merkt dat de pagina-rendering prestaties afnemen.
Requests Rejected Het totaal aantal aanvragen die niet uitgevoerd zijn omdat er onvoldoende resources van de server zijn om ze te verwerken. Deze counter geeft het aantal verzoeken om een 503 HTTP status code terug te geven weer en dit geeft aan dat de server te druk is..
Requests Executing (_Total) Het aantal verzoeken die momenteel uitgevoerd worden.

 

Requests/Sec (_Total) Het aantal verzoeken die per seconde worden uitgevoerd. Dit komt overeen met de huidige verwerkingscapaciteit van de  applicatie. Onder constante belasting, dient dit aantal gelijk te blijven binnen een bepaald bereik, behoudens het andere server werk (zoals ‘garbage collection’, ‘cache cleanup thread’, ‘external server tools’, etc.).
.NET CLR Memory  
# Gen 0 Collections Geeft het aantal keren dat de generatie 0 objecten (dat wil zeggen, de jongste, meest recent toegewezen objecten) zijn verzameld als ‘garbage’ (vuil) sinds de toepassing is gestart.
# Gen 1 Collections Geeft het aantal keren weer dat de generatie 1 objecten verzameld zijn als garbage sinds de applicatie is gestart
# Gen 2 Collections Geeft het aantal keren dat de generatie 2 objecten verzameld zijn als garbage zijn verzameld sinds de applicatie is gestart weer. De counter wordt verhoogd aan het eind van generatie 2 ‘garbage collection’ (ook wel volledige ‘garbage collection’)
% Time in GC Geeft het percentage van de verstreken tijd die werd bestaad aan het uitvoeren van een garbage collection weer sinds de laaste garbage collection cyclus. Deze counter geeft het werk van de garbage collector weer.

SQL Server Counters
Als aanvulling op het systeem en de Web gerelateerde performance counters, dient men ook de SQL servers in de gaten te houden. Ook de counters dient men in de gaten te houden. Onderstaande lijst geeft weer welke counters beschikbaar zijn.

Objecten en counters Omschrijving
General Statistics Dit object biedt counters om de algemene server activiteit te monitoren, zoals bijvoorbeeld het nummer van de momenteel aanwezige verbindingen en het aantal gebruikers die verbonden zijn en afmelden per seconde van computers die gebruik maken van de SQL server.
User Connections Deze counter geeft de hoeveelehid gebruiker-aansluitingen op uw SQL server weer. Als dit nummer stijgt met 500% vanaf de baseline, kan men een prestatievermindering waarnemen.

 

Databases Dit object biedt counters om ‘bulk copy operations, ‘backup and restore’ en ‘transactions log activities’ te monitoren. Het monitoren van ‘low-level log’ activiteiten geeft inzicht om bottlenecks te identificeren.

 

Transactions/sec Deze counters geeft het aantal transacties voor een bepaalde database of voor de gehele SQL server per seconde weer. Het nummer helpt om een baseline te ontwerpen en helpt bij het oplossen van problemen.
Locks Dit object geeft informatie over de SQL server ‘locks’ op individuele brontypes.
Number of Deadlocks/sec Deze counter geeft het aantal ‘deadlocks’ op de SQL server per seconde weer. Dit is normaal gesproken 0.
Average Wait Time (ms) Deze counter geeft de gemiddelde wachttijd voor elke ‘lock’ weer.
Lock Wait Time (ms) Deze counter geeft de totale wachttijd voor ‘locks’ in de laaste seconde weer.
Lock Waits/sec Deze counter toont het aantal locks per seconde die niet onmiddelijk voldaan konden worden en moesten wachten op bronnen.
Latches Dit object biedt counters om de interne SQL server ‘resource locks’ (ook wel latches genaamd) te monitoren.
Average Latch Wait Time (ms) Deze counter geeft het gemiddelde vergrendel wachttijd weer voor verzoeken die moesten wachten.
Latch Waits/se Deze counter toont het aantal vergrendel verzoeken per seconde die onmiddel warden uitgevoerd weer.
SQL Statistics Dit object biedt counters om de compilatie en het type verzoek te monitoren.
SQL Compilations/sec Deze counter geeft het aantal keer dat het compile code path per seconden is doorlopen weer.
SQL Re-Compilations/sec Deze counter geeft het aantal keer dat de ‘statement recompiles’ zijn getriggerd per seconde weer.
Plan Cache Dit object biedt counters om te monitoren hoe de SQL server gebruik maakt van het geheugen om objecten op te slaan.

.

Cache Hit Ratio Deze counter geeft de verhouding tussen de ‘chache hits’ en de ‘lookups’ voor de plannen weer.
Buffer Cache Dit object biedt counters om te monitoren hoe de SQL server gebruikt maakt van het geheugen om data pagina’s op te slaan en dergelijke.
Buffer Cache Hit Ratio Deze counter toont het percentage van de pagina’s in de ‘buffer chache’ zonder dat deze vanaf de schijf warden gelezen. De verhouding is het totale aantal chache treffers gedeeld door het totale aantal chace lookups sinds de SQL server is gestart.
General Statistics Dit object biedt counters om de algemene server activiteiten te monitoren. Deze activiteiten zijnbijvoorbeeld het aantal verbindingen, het aantal gebruikers die verbinding maken met de SQL server enzovoorts.

Dit is de volledige lijst met beschikbare system objecten en performance counters die u kunt toevoegen aan uw SharePoint 2010 monitoring oplossing.

Thursday, April 26th, 2012

Generieke server monitoring met Monitis en M3
Een kat die achter een muis aan zit zou met behulp van Monitis gemonitord kunnen worden. Door de toevoeging van M3 is het mogelijk om alles te monitoren. Dit alleen is natuurlijk verreweg van genoeg. De implementatie van ‘slimme’ applicatie monitoring is wat men moet beoefenen.
Dit hele artikel gaat over het harde werk wat Konstatin Kosenkov in M3 heeft gestopt. Hij verdient alle eer. Konstatin heeft het voor elkaar gekregen om een aantal counters in een PostgreSQL (ook wel PgSQL) installatie te ontwerpen en te implementeren.

PostgreSQL in een notendop
PgSQL is een open source, cross platform implementatatie van een relationele database. Er zijn een paar gelijkenissen met MySQL. PgSQL is erg popuair. Het is wereldwijd bekend en Monitis heeft besloten dat het tijd was om een uitgebreide set van monitoren te bouwen om te voorzien in effectieve server monitoring waarmee de uptime verhoogd kan worden als men gebruikt maakt van PgSQL.
Ook al gebruikt u geen PgSQL, lees dan toch verder want de monitors en counters die in dit artikel aan bod komen zijn van grote waarde voor een database installatie, ook al is het geen PgSQL. Er zullen nu een aantal counters opgesomd worden.

Operating system counters (besturingssysteem counters)
Open het M3 configuratie bestand voordat u verder gaat met lezen. Dit bestand zorgt ervoor dat de dingen een stuk helderder worden. De eerste twee monitors die geïmplementeerd zijn, zijn geen PgSQL counters. Ze geven echter wel een duidelijk beeld van wat er gebeurd in de systemen, de eerste drie counters laten de CPU zien terwijl de vierde counter het gemiddelde van de CPU laat zien. De volgende twee counters in de volgende monitor laten de schrijf en lees verzoeken per seconde aan het PgSQL apparaat zien. Kijkend naar deze twee monitors in Monitis zou een goed beeld moeten geven of het systeem overbelast is of niet.

Transacties per seconde (TPS)
TSP geeft een goed beeld van hoe druk het systeem bezig is en hoe snel uw bedrijf en applicaties groeien. Deze combinatie zijn de ‘Rush hours’ van uw bedrijf.
Een andere insteek om de TSP te monitoren is het verminderen van deze transacties van en naar de database. TSP wordt gemeten door middel van een simpele query. M3 maakt een query van het totaal aantal transacties, deze transacties worden nog een keer in een query gezet en dan wordt het verschil tussen deze tijden gemeten.

Cache Hit Ratio & Commit Ratio
Iedere database implementatie streeft erna om zoveel mogelijk data in te laden in het geheugen (RAM). Wanneer een query is gemaakt en opgesteld door middel van data die verkregen is uit het geheugen van de database, noemt men dit een ‘chache hit’. Indien de database de data van een schijf moet halen, heet dit een ‘cache miss’.
De ‘Hit Ratio’ counter laat zien hoe de database de data chached. Hoe hoger deze waarde waarde hoe beter. Dit wil zeggen dat de queries sneller worden terruggegeven.
‘Commit Ratio’ laat zien hoeveel succesvolle ‘commits’ (schrijfacties) er daadwerkelijk in de PgSQL waren. Alle waarden die lager zijn dan 80-90% kunnen op een probleem duiden.

Database I/O – Cache hits versus Blocks read
Er zullen twee counters van deze monitor besproken worden:

  1. Blocks gelezen door PgSQL
  2. Chache Hits door PgSQL

Deze twee counters zijn gekoppeld in een andere monitor om een beter beeld te geven betreft de ‘Chache Hit Ratio’ counter, die hierboven is besproken. Het verdelen van Chache hits in blokken geeft de Chache hit ratio als uitkomst. Hoe beter de PgSQL presteert, hoe minder er vanaf de schijf gehaald wordt en hoe meer vanuit het geheugen.

Gebruikers verbindingen versus het maximaal aantal gebruikers verbindingen
Deze monitor legt zichzelf  uit. Deze monitor laat namelijk het aantal huidige gebruikers zien die verbonden zijn en de monitor laat ook het maximaal aantal gebruikers dat de PgSQL aankan zien.

Memory & disk footprint
Deze monitors zijn erg simpel. Ze laten zien hoe veel de PgSQL verbruikt van je hele systeem. De geheugen counters laten een totaal zien van de hele server en het totaal gebruik van de PgSQL . Hetzelfde geldt voor de schijf. Het instellen van alerts is simpel in Monitis. Deze alerts hebben als doel dat de servers een beter uptime hebben. Zorg dat je de eerste bent of je geen schijfgeheugen meer hebt of de PgSQL meer RAM nodig heeft.

Hoe werkt het?
Kijk hier naar hoe M3 werkt. Wijzig de de M3Templates.pm door de juiste database in te vullen. Deze database moet gemonitord worden. Verder wordt het apparaat, de API en de Secret Key ook ingevuld.

De code:

# ./AddMonitors.pl pgsql_statistics.xml # ./TimerRun.pl pgsql_statistics.xml

Log in op Monitis en het verzamelen van de statistieken kan beginnen! Met Monitis en M3 kan alles gemonitord worden.

Volg ons op Twitter!  

Wednesday, April 25th, 2012

M3 – De custom Monitos Swiss Tool
M3 is er al weer een tijdje en de verbeteringen blijven maar komen. Het is een volwassen infrastructuur voor server monitoring, in combinatie met Monitis. M3 laat de eindgebruik op eenvoudige wijze checks configureren en data uploaden naar Monitis. In dit artikel zullen een aantal van de recente toevoegingen worden weergegeven van M3 en er zal een voorbeeld gegeven worden over het meten van CPU en geheugen.

M3 ‘Compute’ / ‘post process ‘ plugings
Wanneer men ‘ruwe’ monitoring data verzameld, is het soms nodig dat deze data verbloemt wordt door ‘post processing’. Het doel van ‘post processing’ is dus het verfraaien van ruwe monitorgegevens.
M3 ondersteunt deze vorm van plugins, in de ‘Compute’ directory. De README op github geeft een beschrijving van deze plugins.

Voorbeeld: Math.pm
Math.pm zorgt ervoor dat we kunnen vermenigvuldigen, delen, aftrekken of aan het eindresultaat dingen toevoegen. Stel dat men het volgende stuk code uit de configuratie heeft:

<exectemplate>echo 10</exectemplate>
<metric name="Math example">
<type>integer</type>
<uom>number</uom>
   <line>1</line>
     <math>+5</math>
     <math>*9</math>
     <math>-10</math>
     <math>/5</math> </metric>

De uitvoer van deze code op M3 is:

  • ‘parse’ lijn nummer 1 => 10
  • Tel hier 5 bij op => 10 + 5 = 15
  • Vermenigvuldig met 9 => 15 × 9 = 135
  • Trek hier 10 vanaf => 135 – 10 = 125
  • Deel door 5 => 125 / 5 = 25

Zoals men kan zien, kunnen ‘compute plugings’ makkelijk met elkaar verbonden worden en het gebruik ervan is simpel. Indien je de omzetting van MBytes naar Kbytes en vice versa wilt maken, of een of ander ‘computional’ ‘post processing operation’, helpen de compute plugings. Naast de Math.pm plugin is er ook een plugin beschikbaar die de gemiddelden berekend en er is een plugin die de ‘diff’ per seconde berekend. Raadpleeg de README voor voorbeelden en het gebruik van de plugings.

M3 Linux Statistcs Pluging
De Linux Statistics pluging is een plugin voor M3 die gebruik maakt van de Perl module om de prestatie counters van het systeem, zoals CPU en geheugen verbruik, uit je systeem te halen. Het gebruik is eenvoudig beschreven en alles is gedocumenteerd in de README. Hier is een voorbeeld over hoe het schijfgebruik van /dev/sda1 opgehaald kan worden:

<monitor name="Disk monitor for /dev/sda1">
<linuxsysstats>diskusage->{'/dev/sda1'}{total}</linuxsysstats>
<linuxsysstats>diskusage->{'/dev/sda1'}{usage}</linuxsysstats> <metric name="Total">
<type>integer</type> <uom>KB</uom> <line>1</line> </metric> <metric name="Used">
<type>integer</type> <uom>KB</uom> <line>2</line> </metric> </monitor>

Meer voorbeelden zijn hier te vinden: Perl Linux Statistics module

Het automatisch toevoegen van monitors
Een tijdje geleden moest onderstaande code uitgevoerd worden. Deze code zorgde ervoor dat er ‘Custom Monitors’ werden toegevoegd aan Monitis, voordat de data update plaats kon vinden.

# ./AddMonitors.pl config.xml

Tegenwoordig wordt dit automatisch gedaan. Het uploaden kan gestart worden door een van onderstaande ‘executables’ te starten:

TimberRun.pl
Run.pl

Deze twee ‘executables’ zorgen ervoor dat de monitors op correcte wijze aangemaakt worden.

Data chaching
Tegenwoordig is het niet raar dat er netwerkstoringen plaatsvinden. Nog niet zo heel lang geleden, zou M3 tijdens het uploaden van data stoppen met dit proces. Nu M3 is vernieuwd, is het zo dat wanneer er een netwerkstoring optreedt, de gegevens opgeslagen worden en wanneer de verbinding weer terug is, worden de gegevens geupload naar Monitis. Dit noemt men data chaching. Dit is natuurlijk ideaal voor performance monitoring, waardoor dit een stuk betrouwbaarder is.

Het is business time!
Het doel was nu om een gemiddelde tijd van de CPU en het geheugen gebruik grafisch weer te geven. Open dit configuratiebestand terwijl je verder gaat met het lezen van dit artikel.Er zijn twee monitors, een voor de CPU en een voor het geheugen. Deze twee monitors voeren allebei een Linux Statistics command uit. De interval is ingesteld op 10 seconden, wat inhoudt dat de CPU en het geheugen iedere 10 seconden wordt gemeten. Monitis maakt echter gebruik van de <avg>, de Average.pm compute module.

De Average.pm module ontvangt een nummer, bijvoorbeeld 30. Dan berekent de module het gemiddelde van iedere 30 checks. Als we dus iedere 10 seconden een check doen, en het gemiddelde van 30 meetpunten pakken, is dit dus een gemiddelde van 5 minuten (300 seconden). In onderstaande afbeelding wordt dit weergegeven.

Overhead of géén overhead!
M3 is een uitgebreide aanvulling op Monitis. De combinatie van Monitis met M3 zorgt ervoor dat alles gemonitord kan worden. Dit is ook aangetoond in voorgaande artikelen. M3 heeft een lichte ‘memory overhead’ wanneer het gebruik maakt van de verschillende Perl Modules, maar de daadwerkelijke grootte is rond de 30MBytes. 30MBytes om alles te monitoren. In termen van CPU overhead, kan de M3 de hele dag draaien op een Netbook, zonder dat je het door hebt! Geloof je dit niet? Probeer het maar!

Met M3 en Monitis kan alles worden gemonitord. Volg ons daarom op Twitter.