IIS WarmUp Part II

IIS WarmUp Part II

Posted:  April 18, 2012

IIS WarmUp Part II

I explained in my earlier post the importance of “warming up” your sites in IIS, especially using the latest .Net frameworks.

Here is a major update to the code posted in that post.

This one will allow you to “warm up” every site in IIS on your server. All you have to do is set the version of IIS to 7 or 6 depending on your install, and then run the program. You could also set the allApplications flag to false and put in the selected sites to “warm up”. Please understand, because of the access needed to warm up all of your sites, this program needs to run under an Administrator account. (it accesses IIS’s metabase files)

So, without too much blab, and without any further ado… here’s the code.

Settings.xml

<Settings>
 <Config>
 <!-- Set your IIS version, and whether or no you want to "warm up" all sites -->
 <IIS version="7" allApplications="True">
 <!-- This is a list of sites to warm up, only comes into play if you have the allApplications flag set to false -->
 <Site url="http://www.o7thwebdesign.com" page="/" />
 <Site url="http://www.facchinifacchinipa.com" page="/" />
 <Site url="http://skor.in" page="/" />
 <Site url="http://o7t.in" page="/" />
 </IIS>
 </Config>
</Settings>

AuditManager.vb

Public Class AuditManager

 'The type of audit to write out
 Public Enum AuditType
 Exception
 General
 End Enum

 'Write the audit to the log file
 Public Shared Sub Write(ByVal _Type As AuditType?, ByVal _Description As String, Optional ByVal _Location As String = Nothing, Optional ByVal _Except As Exception = Nothing)
 Dim _Stack As System.Diagnostics.StackTrace
 If _Except IsNot Nothing Then
 _Stack = New System.Diagnostics.StackTrace(_Except, True)
 Else
 _Stack = Nothing
 End If
 Using _F As New IO.StreamWriter(Common.GetPath() & FormatDateTime(Date.Now, DateFormat.ShortDate).Replace("/", String.Empty) & ".LOG", True)
 Dim tmpString As New Text.StringBuilder
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 tmpString.Append("WHEN:" & vbCrLf)
 tmpString.Append(Date.Now & vbCrLf)
 If _Type.HasValue Then
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 tmpString.Append("TYPE:" & vbCrLf)
 tmpString.Append([Enum].GetName(GetType(AuditType), _Type) & vbCrLf)
 End If
 If _Location IsNot Nothing Then
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 tmpString.Append("LOCATION:" & vbCrLf)
 tmpString.Append(_Location & vbCrLf)
 End If
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 If _Stack IsNot Nothing Then
 tmpString.Append("STACKTRACE:" & vbCrLf)
 tmpString.Append(_Stack.ToString() & vbCrLf)
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 tmpString.Append("STACK FRAMES:" & vbCrLf)
 For Each frame In _Stack.GetFrames()
 tmpString.Append(" - FILE:" & frame.GetFileName() & vbCrLf)
 tmpString.Append(" - METHOD:" & frame.GetMethod().Name & vbCrLf)
 tmpString.Append(" - LINE:" & frame.GetFileLineNumber() & vbCrLf)
 tmpString.Append(" - COLUMN:" & frame.GetFileColumnNumber() & vbCrLf)
 Next
 End If
 If _Except IsNot Nothing Then
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 tmpString.Append("SOURCE:" & vbCrLf)
 tmpString.Append(_Except.Source & vbCrLf)
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 tmpString.Append("MESSAGE:" & vbCrLf)
 tmpString.Append(_Except.Message & vbCrLf)
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 tmpString.Append("DATA:" & vbCrLf)
 tmpString.Append(_Except.Data.ToString() & vbCrLf)
 End If
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 tmpString.Append("NOTES:" & vbCrLf)
 tmpString.Append(_Description & vbCrLf)
 tmpString.Append("-------------------------------------------------" & vbCrLf)
 _F.Write(tmpString.ToString())
 _F.Close()
 End Using
 End Sub

End Class

Common.vb

Public Class Common

 'The applications path
 Public Shared Function GetPath() As String
 Return System.AppDomain.CurrentDomain.BaseDirectory()
 End Function

 'Check to see if a value is Null, if so, set it to equal a default value
 Public Shared Function IsNull(Of T)(ByVal Value As T, ByVal _Default As T) As T
 If Not (IsDBNull(Value)) OrElse Value IsNot Nothing OrElse Not (Value.ToString.Length > 0) Then
 Return DirectCast(Value, T)
 Else
 Return DirectCast(_Default, T)
 End If
 End Function

End Class

CustomCache.vb

Imports System.Runtime.Caching

''' <summary>
''' Our Provider
''' </summary>
''' <remarks></remarks>
Public Interface ICacheProvider
 Function GetItem(Of T)(ByVal key As String) As T
 Sub SetItem(ByVal data As Object, ByVal key As String)
 Sub Remove(ByVal key As String)
 Sub Clear()
End Interface

''' <summary>
''' Our Custom Caching Object
''' </summary>
''' <remarks></remarks>
Public Class CustomCache
 Implements ICacheProvider

 ''' <summary>
 ''' The Cache Object
 ''' </summary>
 ''' <value></value>
 ''' <returns></returns>
 ''' <remarks></remarks>
 Private ReadOnly Property Cache() As ObjectCache
 Get
 Return MemoryCache.Default
 End Get
 End Property

 ''' <summary>
 ''' Set the cache Item
 ''' </summary>
 ''' <param name="key"></param>
 ''' <param name="data"></param>
 ''' <remarks></remarks>
 Public Sub SetCacheItem(ByVal data As Object, ByVal key As String) Implements ICacheProvider.SetItem
 Dim policy As New CacheItemPolicy()
 policy.AbsoluteExpiration = DateTime.Now.AddHours(24)
 Cache.Add(New CacheItem(key, data), policy)
 End Sub

 ''' <summary>
 ''' Get the Cache Item
 ''' </summary>
 ''' <typeparam name="T"></typeparam>
 ''' <param name="key"></param>
 ''' <returns></returns>
 ''' <remarks></remarks>
 Public Function GetCacheItem(Of T)(ByVal key As String) As T Implements ICacheProvider.GetItem
 Return DirectCast(Cache(key), T)
 End Function

 ''' <summary>
 ''' Remove the Item from Cache
 ''' </summary>
 ''' <param name="key"></param>
 ''' <remarks></remarks>
 Public Sub RemoveItem(ByVal key As String) Implements ICacheProvider.Remove
 Cache.Remove(key)
 End Sub

 ''' <summary>
 ''' Remove All items from Cache
 ''' </summary>
 ''' <remarks></remarks>
 Public Sub ClearCache() Implements ICacheProvider.Clear
 For Each item In Cache
 Cache.Remove(item.Key)
 Next
 End Sub

End Class

Settings.vb

Public Class Settings

 Private Shared Cache As New CustomCache

 'Grab our settings file
 Private Shared ReadOnly Property SettingDoc As XDocument
 Get
 Dim _C As XDocument = Cache.GetCacheItem(Of XDocument)("Settings")
 If _C IsNot Nothing Then
 Return _C
 Else
 Return XDocument.Load(Common.GetPath() & "Settings.xml")
 End If
 End Get
 End Property

 'Get and set all our settings
 Public Shared Function GetSettings() As List(Of Typing.Settings.Settings)
 Dim _Qry As New List(Of Typing.Settings.Settings)
 _Qry = (From n In SettingDoc...<IIS>.AsParallel()
 Select New Typing.Settings.Settings() With {
 .IisVersion = Common.IsNull(Of Integer)(n.@version, 0),
 .PrimeAll = Common.IsNull(Of Boolean)(n.@allApplications, True),
 .Sites = Common.IsNull(Of List(Of Typing.Settings.Sites))((From s In n.<Site>.AsParallel()
 Select New Typing.Settings.Sites() With {
 .Url = s.@url,
 .Page = s.@page
 }).ToList(), Nothing)
 }).ToList()
 If _Qry IsNot Nothing Then
 Return _Qry
 Else
 Return Nothing
 End If
 _Qry.Clear()
 End Function

End Class

Typing.vb

'Strongly Type all our values
Public Class Typing

 Partial Public Class Settings

 Partial Public Class Settings
 Public Property IisVersion As Integer
 Public Property PrimeAll As Boolean
 Public Property Sites As List(Of Sites)
 End Class

 Partial Public Class Sites
 Public Property Url As String
 Public Property Page As String
 End Class

 End Class

 Partial Public Class MetaBase
 Public Property Protocol As String
 Public Property Binding As String
 End Class

End Class

WarmUpService.vb

Imports System.Threading.Tasks
Imports System.Security.Principal

Module WarmUpService

 'Check and make sure we have Admin Privelages
 Private ReadOnly Property HasAdminPrivelages()
 Get
 Dim _Id = WindowsIdentity.GetCurrent()
 Dim _Prin = New WindowsPrincipal(_Id)
 Return _Prin.IsInRole(WindowsBuiltInRole.Administrator)
 End Get
 End Property

 'Fire It Up!
 Public Sub Main()
 If HasAdminPrivelages() Then
 AuditManager.Write(AuditManager.AuditType.General, "Fireing Up...")
 DoTheWarmUp()
 AuditManager.Write(AuditManager.AuditType.General, "All Set...")
 Else
 MsgBox("You need to be an administrator in order to run this.")
 End If
 End Sub

 Private Sub DoTheWarmUp()
 Try
 Dim _Set As List(Of Typing.Settings.Settings) = Settings.GetSettings()
 If _Set IsNot Nothing Then
 If _Set(0).PrimeAll Then
 Select Case _Set(0).IisVersion
 Case 6 ' IIS 6
 Dim _PT As New Iis6Primer()
 _PT.PrimeThem()
 Case 7 ' IIS 7 & IIS 7.5
 Dim _PT As New Iis7Primer()
 _PT.PrimeThem()
 Case Else
 AuditManager.Write(AuditManager.AuditType.Exception, "There was an issue! Unsupported IIS version.", "DoTheWarmUp")
 End Select
 Else
 Dim _Sites As List(Of Typing.Settings.Sites) = _Set.Item(0).Sites
 If _Sites IsNot Nothing Then
 Parallel.ForEach(_Sites, Sub(Item)
 Primer.GrabEm(Item.Url & Item.Page)
 End Sub)
 _Sites.Clear()
 End If
 _Set.Clear()
 End If
 Else
 AuditManager.Write(AuditManager.AuditType.Exception, "There was an issue! There are no settings.", "DoTheWarmUp")
 End If
 Catch ex As Exception
 AuditManager.Write(AuditManager.AuditType.Exception, "There was an issue!", "DoTheWarmUp", ex)
 End Try
 End Sub

End Module

Primer.vb

Imports System.Net
Imports System.Reflection

Public Class Primer

 Public Shared Sub GrabEm(ByVal _SitePath As String)
 Try
 SetAllowUnsafeHeaderParsing20()
 Using _WC As New WebClient()
 _WC.Headers.Add("user-agent", "Mozilla/5.0 (Windows; U; Windows NT 6.1; en-US; rv:1.9.2.13) Gecko/20101203 Firefox/3.6.13")
 _WC.DownloadData(_SitePath)
 End Using
 AuditManager.Write(AuditManager.AuditType.General, "Site: " & _SitePath & " Is Now Primed!")
 Catch ex As Exception
 AuditManager.Write(AuditManager.AuditType.Exception, "Issue with the site: " & _SitePath & ".", "GrabEm", ex)
 End Try
 End Sub

 Private Shared Sub SetAllowUnsafeHeaderParsing20()
 Dim a As New System.Net.Configuration.SettingsSection
 Dim aNetAssembly As System.Reflection.Assembly = Assembly.GetAssembly(a.GetType)
 Dim aSettingsType As Type = aNetAssembly.GetType("System.Net.Configuration.SettingsSectionInternal")
 Dim args As Object() = Nothing
 Dim anInstance As Object = aSettingsType.InvokeMember("Section", BindingFlags.Static Or BindingFlags.GetProperty Or BindingFlags.NonPublic, Nothing, Nothing, args)
 Dim aUseUnsafeHeaderParsing As FieldInfo = aSettingsType.GetField("useUnsafeHeaderParsing", BindingFlags.NonPublic Or BindingFlags.Instance)
 aUseUnsafeHeaderParsing.SetValue(anInstance, True)
 End Sub

End Class

Iis6Primer.vb

Imports <xmlns="urn:microsoft-catalog:XML_Metabase_V64_0">
Imports System.Threading.Tasks

Public Class Iis6Primer

 Private _Xml As XDocument
 Dim _Qry As New List(Of Typing.MetaBase)

 Public Sub New()
 Dim _MetaBasePath As String = Environment.GetFolderPath(Environment.SpecialFolder.System) & "inetsrv"
 _MetaBasePath += "metabase.xml"
 _Xml = XDocument.Load(_MetaBasePath, LoadOptions.PreserveWhitespace)
 _Qry = (From n In _Xml...<IIsWebServer>
 Where (n.@ServerBindings IsNot Nothing)
 Select New Typing.MetaBase() With {
 .Binding = Common.IsNull(Of String)(n.@ServerBindings, String.Empty)
 }).ToList()
 End Sub

 Public Sub PrimeThem()
 Dim _Binding, _Url, _T
 Parallel.ForEach(_Qry, Sub(Item)
 _Binding = Item.Binding
 If _Binding.Contains(" ") Then
 _Binding = _Binding.Replace(" ", "|")
 _T = _Binding.Split("|")
 For Each i In _T
 _Url = i.Split(":")
 If _Url(1).Contains("80") Then
 Primer.GrabEm("http://" & _Url(_Url.GetUpperBound(0)))
 End If
 Next
 Else
 _Url = _Binding.Split(":")
 If _Url(1).Contains("80") Then
 Primer.GrabEm("http://" & _Url(_Url.GetUpperBound(0)))
 End If
 End If
 End Sub)
 _Qry.Clear()
 End Sub

End Class

Iis7Primer.vb

Imports System.Threading.Tasks

Public Class Iis7Primer

 Private _Xml As XDocument
 Dim _Qry As New List(Of Typing.MetaBase)

 Public Sub New()
 Dim _MetaBasePath As String = Environment.GetFolderPath(Environment.SpecialFolder.System) & "inetsrv"
 _MetaBasePath += "configapplicationHost.config"
 _Xml = XDocument.Load(_MetaBasePath, LoadOptions.PreserveWhitespace)
 _Qry = (From n In _Xml...<binding>.AsParallel()
 Select New Typing.MetaBase() With {
 .Binding = Common.IsNull(Of String)(n.@bindingInformation, String.Empty),
 .Protocol = Common.IsNull(Of String)(n.@protocol, String.Empty)
 }).ToList()
 End Sub

 Public Sub PrimeThem()
 Dim _Prot, _Binding, _Url
 Parallel.ForEach(_Qry, Sub(i)
 _Prot = i.Protocol
 If _Prot = "http" Then
 _Binding = i.Binding
 _Url = _Binding.Split(":")
 Primer.GrabEm("http://" & _Url(_Url.GetUpperBound(0)))
 End If
 End Sub)
 _Qry.Clear()
 End Sub

End Class

 

Kevin Pirnie

20+ Years of PC and server maintenance & over 15+ years of web development/design experience; you can rest assured that I take every measure possible to ensure your computers are running to their peak potentials. I treat them as if they were mine, and I am quite a stickler about keeping my machines up to date and optimized to run as well as they can.

Cookie Notice

This site utilizes cookies to improve your browsing experience, analyze the type of traffic we receive, and serve up proper content for you. If you wish to continue browsing, you must agree to allow us to set these cookies. If not, please visit another website.

Privacy Policy

Revised: June 8, 2021

Thank you for choosing to be part of my website at https://kevinpirnie.com (“Company”, “I”, “me”, “mine”). I am committed to protecting your personal information and your right to privacy. If you have any questions or concerns about this privacy notice, or my practices with regards to your personal information, please contact me at .

When you visit my website https://kevinpirnie.com (the “Website”), and more generally, use any of my services (the “Services”, which include the Website), I appreciate that you are trusting me with your personal information. I take your privacy very seriously. In this privacy notice, I seek to explain to you in the clearest way possible what information we collect, how I use it and what rights you have in relation to it. I hope you take some time to read through it carefully, as it is important. If there are any terms in this privacy notice that you do not agree with, please discontinue use of my Services immediately.

This privacy notice applies to all information collected through my Services (which, as described above, includes our Website), as well as, any related services, sales, marketing or events.

Please read this privacy notice carefully as it will help you understand what I do with the information that I collect.

1. WHAT INFORMATION DO I COLLECT?

Information automatically collected

In Short: Some information – such as your Internet Protocol (IP) address and/or browser and device characteristics – is collected automatically when you visit my Website.

I automatically collect certain information when you visit, use or navigate the Website. This information does not reveal your specific identity (like your name or contact information) but may include device and usage information, such as your IP address, browser and device characteristics, operating system, language preferences, referring URLs, device name, country, location, information about how and when you use our Website and other technical information. This information is primarily needed to maintain the security and operation of our Website, and for our internal analytics and reporting purposes.

Like many businesses, I also collect information through cookies and similar technologies.

The information I collect includes:
Log and Usage Data. Log and usage data is service-related, diagnostic, usage and performance information our servers automatically collect when you access or use our Website and which we record in log files. Depending on how you interact with us, this log data may include your IP address, device information, browser type and settings and information about your activity in the Website (such as the date/time stamps associated with your usage, pages and files viewed, searches and other actions you take such as which features you use), device event information (such as system activity, error reports (sometimes called ‘crash dumps’) and hardware settings).

Device Data. I collect device data such as information about your computer, phone, tablet or other device you use to access the Website. Depending on the device used, this device data may include information such as your IP address (or proxy server), device and application identification numbers, location, browser type, hardware model Internet service provider and/or mobile carrier, operating system and system configuration information.

Location Data. I collect location data such as information about your device’s location, which can be either precise or imprecise. How much information I collect depends on the type and settings of the device you use to access the Website. For example, I may use GPS and other technologies to collect geolocation data that tells me your current location (based on your IP address). You can opt out of allowing me to collect this information either by refusing access to the information or by disabling your Location setting on your device. Note however, if you choose to opt out, you may not be able to use certain aspects of the Services.

2. HOW DO I USE YOUR INFORMATION?

In Short: I process your information for purposes based on legitimate business interests, the fulfillment of my contract with you, compliance with my legal obligations, and/or your consent.

I use personal information collected via my Website for a variety of business purposes described below. I process your personal information for these purposes in reliance on my legitimate business interests, in order to enter into or perform a contract with you, with your consent, and/or for compliance with my legal obligations. I indicate the specific processing grounds I rely on next to each purpose listed below.

For other business purposes. I may use your information for other business purposes, such as data analysis, identifying usage trends, determining the effectiveness of our promotional campaigns and to evaluate and improve my Website, products, marketing and your experience. I may use and store this information in aggregated and anonymized form so that it is not associated with individual end users and does not include personal information. I will not use identifiable personal information without your consent.

3. WILL YOUR INFORMATION BE SHARED WITH ANYONE?

In Short: I only share information with your consent, to comply with laws, to provide you with services, to protect your rights, or to fulfill business obligations.

4. DO WE USE COOKIES AND OTHER TRACKING TECHNOLOGIES?

In Short: I may use cookies and other tracking technologies to collect and store your information.

I may use cookies and similar tracking technologies (like web beacons and pixels) to access or store information. Specific information about how I use such technologies and how you can refuse certain cookies is set out in our Cookie Notice.

5. IS YOUR INFORMATION TRANSFERRED INTERNATIONALLY?

In Short: We may transfer, store, and process your information in countries other than your own.

My servers are located in the United States of America, unless otherwise requested by my clients. If you are accessing my Website from outside, please be aware that your information may be transferred to, stored, and processed by me in my facilities and by those third parties with whom I may share your personal information (see “WILL YOUR INFORMATION BE SHARED WITH ANYONE?” above), in and other countries.

If you are a resident in the European Economic Area, then these countries may not necessarily have data protection laws or other similar laws as comprehensive as those in your country. I will however take all necessary measures to protect your personal information in accordance with this privacy notice and applicable law.

6. HOW LONG DO WE KEEP YOUR INFORMATION?

In Short: I keep your information for as long as necessary to fulfill the purposes outlined in this privacy notice unless otherwise required by law.

I will only keep your personal information for as long as it is necessary for the purposes set out in this privacy notice, unless a longer retention period is required or permitted by law (such as tax, accounting or other legal requirements). No purpose in this notice will require me keeping your personal information for longer than 6 months.

When I have no ongoing legitimate business need to process your personal information, I will either delete or anonymize such information, or, if this is not possible (for example, because your personal information has been stored in backup archives), then I will securely store your personal information and isolate it from any further processing until deletion is possible.

7. HOW DO WE KEEP YOUR INFORMATION SAFE?

In Short: I aim to protect your personal information through a system of organizational and technical security measures.

I have implemented appropriate technical and organizational security measures designed to protect the security of any personal information I process. However, despite our safeguards and efforts to secure your information, no electronic transmission over the Internet or information storage technology can be guaranteed to be 100% secure, so I cannot promise or guarantee that hackers, cybercriminals, or other unauthorized third parties will not be able to defeat my security, and improperly collect, access, steal, or modify your information. Although I will do my best to protect your personal information, transmission of personal information to and from my Website is at your own risk. You should only access the Website within a secure environment.

8. DO WE COLLECT INFORMATION FROM MINORS?

In Short: I do not knowingly collect data from or market to children under 18 years of age.

I do not knowingly solicit data from or market to children under 18 years of age. By using the Website, you represent that you are at least 18 or that you are the parent or guardian of such a minor and consent to such minor dependent’s use of the Website. If I learn that personal information from users less than 18 years of age has been collected, I will deactivate the account and take reasonable measures to promptly delete such data from my records. If you become aware of any data I may have collected from children under age 18, please contact me at .

9. WHAT ARE YOUR PRIVACY RIGHTS?

In Short: You may review, change, or terminate your account at any time.

If you are a resident in the European Economic Area and you believe I am unlawfully processing your personal information, you also have the right to complain to your local data protection supervisory authority. You can find their contact details here: http://ec.europa.eu/justice/data-protection/bodies/authorities/index_en.htm.

If you are a resident in Switzerland, the contact details for the data protection authorities are available here: http://ec.europa.eu/justice/data-protection/bodies/authorities/index_en.htm.

Cookies and similar technologies: Most Web browsers are set to accept cookies by default. If you prefer, you can usually choose to set your browser to remove cookies and to reject cookies. If you choose to remove cookies or reject cookies, this could affect certain features or services of my Website.

10. CONTROLS FOR DO-NOT-TRACK FEATURES

Most web browsers and some mobile operating systems and mobile applications include a Do-Not-Track (“DNT”) feature or setting you can activate to signal your privacy preference not to have data about your online browsing activities monitored and collected. At this stage no uniform technology standard for recognizing and implementing DNT signals has been finalized. As such, I do not currently respond to DNT browser signals or any other mechanism that automatically communicates your choice not to be tracked online. If a standard for online tracking is adopted that I must follow in the future, I will inform you about that practice in a revised version of this privacy notice.

11. DO CALIFORNIA RESIDENTS HAVE SPECIFIC PRIVACY RIGHTS?

In Short: Yes, if you are a resident of California, you are granted specific rights regarding access to your personal information.

California Civil Code Section 1798.83, also known as the “Shine The Light” law, permits my users who are California residents to request and obtain from me, once a year and free of charge, information about categories of personal information (if any) I disclosed to third parties for direct marketing purposes and the names and addresses of all third parties with which I shared personal information in the immediately preceding calendar year. If you are a California resident and would like to make such a request, please submit your request in writing to me using the contact information provided below.

If you are under 18 years of age, reside in California, and have a registered account with the Website, you have the right to request removal of unwanted data that you publicly post on the Website. To request removal of such data, please contact us using the contact information provided below, and include the email address associated with your account and a statement that you reside in California. I will make sure the data is not publicly displayed on the Website, but please be aware that the data may not be completely or comprehensively removed from all my systems (e.g. backups, etc.).

12. DO I MAKE UPDATES TO THIS NOTICE?

In Short: Yes, I will update this notice as necessary to stay compliant with relevant laws.

I may update this privacy notice from time to time. The updated version will be indicated by an updated “Revised” date and the updated version will be effective as soon as it is accessible. If I make material changes to this privacy notice, I may notify you either by prominently posting a notice of such changes or by directly sending you a notification. We encourage you to review this privacy notice frequently to be informed of how I am protecting your information.

13. HOW CAN YOU CONTACT ME ABOUT THIS NOTICE?

If you have questions or comments about this notice, you may email me at or by post to:

Kevin C. Pirnie

22 Orlando St.
Feeding Hills, MA 01030
United States of America

14. HOW CAN YOU REVIEW, UPDATE, OR DELETE THE DATA I COLLECT FROM YOU?

Based on the applicable laws of your country, you may have the right to request access to the personal information I collect from you, change that information, or delete it in some circumstances. To request to review, update, or delete your personal information, you may email me at or by post to:

Kevin C. Pirnie

22 Orlando St.
Feeding Hills, MA 01030
United States of America

Our Privacy Policy

Revised: June 8, 2021

Thank you for choosing to be part of my website at https://kevinpirnie.com (“Company”, “I”, “me”, “mine”). I am committed to protecting your personal information and your right to privacy. If you have any questions or concerns about this privacy notice, or my practices with regards to your personal information, please contact me at .

When you visit my website https://kevinpirnie.com (the “Website”), and more generally, use any of my services (the “Services”, which include the Website), I appreciate that you are trusting me with your personal information. I take your privacy very seriously. In this privacy notice, I seek to explain to you in the clearest way possible what information we collect, how I use it and what rights you have in relation to it. I hope you take some time to read through it carefully, as it is important. If there are any terms in this privacy notice that you do not agree with, please discontinue use of my Services immediately.

This privacy notice applies to all information collected through my Services (which, as described above, includes our Website), as well as, any related services, sales, marketing or events.

Please read this privacy notice carefully as it will help you understand what I do with the information that I collect.

1. WHAT INFORMATION DO I COLLECT?

Information automatically collected

In Short: Some information – such as your Internet Protocol (IP) address and/or browser and device characteristics – is collected automatically when you visit my Website.

I automatically collect certain information when you visit, use or navigate the Website. This information does not reveal your specific identity (like your name or contact information) but may include device and usage information, such as your IP address, browser and device characteristics, operating system, language preferences, referring URLs, device name, country, location, information about how and when you use our Website and other technical information. This information is primarily needed to maintain the security and operation of our Website, and for our internal analytics and reporting purposes.

Like many businesses, I also collect information through cookies and similar technologies.

The information I collect includes:
Log and Usage Data. Log and usage data is service-related, diagnostic, usage and performance information our servers automatically collect when you access or use our Website and which we record in log files. Depending on how you interact with us, this log data may include your IP address, device information, browser type and settings and information about your activity in the Website (such as the date/time stamps associated with your usage, pages and files viewed, searches and other actions you take such as which features you use), device event information (such as system activity, error reports (sometimes called ‘crash dumps’) and hardware settings).

Device Data. I collect device data such as information about your computer, phone, tablet or other device you use to access the Website. Depending on the device used, this device data may include information such as your IP address (or proxy server), device and application identification numbers, location, browser type, hardware model Internet service provider and/or mobile carrier, operating system and system configuration information.

Location Data. I collect location data such as information about your device’s location, which can be either precise or imprecise. How much information I collect depends on the type and settings of the device you use to access the Website. For example, I may use GPS and other technologies to collect geolocation data that tells me your current location (based on your IP address). You can opt out of allowing me to collect this information either by refusing access to the information or by disabling your Location setting on your device. Note however, if you choose to opt out, you may not be able to use certain aspects of the Services.

2. HOW DO I USE YOUR INFORMATION?

In Short: I process your information for purposes based on legitimate business interests, the fulfillment of my contract with you, compliance with my legal obligations, and/or your consent.

I use personal information collected via my Website for a variety of business purposes described below. I process your personal information for these purposes in reliance on my legitimate business interests, in order to enter into or perform a contract with you, with your consent, and/or for compliance with my legal obligations. I indicate the specific processing grounds I rely on next to each purpose listed below.

For other business purposes. I may use your information for other business purposes, such as data analysis, identifying usage trends, determining the effectiveness of our promotional campaigns and to evaluate and improve my Website, products, marketing and your experience. I may use and store this information in aggregated and anonymized form so that it is not associated with individual end users and does not include personal information. I will not use identifiable personal information without your consent.

3. WILL YOUR INFORMATION BE SHARED WITH ANYONE?

In Short: I only share information with your consent, to comply with laws, to provide you with services, to protect your rights, or to fulfill business obligations.

4. DO WE USE COOKIES AND OTHER TRACKING TECHNOLOGIES?

In Short: I may use cookies and other tracking technologies to collect and store your information.

I may use cookies and similar tracking technologies (like web beacons and pixels) to access or store information. Specific information about how I use such technologies and how you can refuse certain cookies is set out in our Cookie Notice.

5. IS YOUR INFORMATION TRANSFERRED INTERNATIONALLY?

In Short: We may transfer, store, and process your information in countries other than your own.

My servers are located in the United States of America, unless otherwise requested by my clients. If you are accessing my Website from outside, please be aware that your information may be transferred to, stored, and processed by me in my facilities and by those third parties with whom I may share your personal information (see “WILL YOUR INFORMATION BE SHARED WITH ANYONE?” above), in and other countries.

If you are a resident in the European Economic Area, then these countries may not necessarily have data protection laws or other similar laws as comprehensive as those in your country. I will however take all necessary measures to protect your personal information in accordance with this privacy notice and applicable law.

6. HOW LONG DO WE KEEP YOUR INFORMATION?

In Short: I keep your information for as long as necessary to fulfill the purposes outlined in this privacy notice unless otherwise required by law.

I will only keep your personal information for as long as it is necessary for the purposes set out in this privacy notice, unless a longer retention period is required or permitted by law (such as tax, accounting or other legal requirements). No purpose in this notice will require me keeping your personal information for longer than 6 months.

When I have no ongoing legitimate business need to process your personal information, I will either delete or anonymize such information, or, if this is not possible (for example, because your personal information has been stored in backup archives), then I will securely store your personal information and isolate it from any further processing until deletion is possible.

7. HOW DO WE KEEP YOUR INFORMATION SAFE?

In Short: I aim to protect your personal information through a system of organizational and technical security measures.

I have implemented appropriate technical and organizational security measures designed to protect the security of any personal information I process. However, despite our safeguards and efforts to secure your information, no electronic transmission over the Internet or information storage technology can be guaranteed to be 100% secure, so I cannot promise or guarantee that hackers, cybercriminals, or other unauthorized third parties will not be able to defeat my security, and improperly collect, access, steal, or modify your information. Although I will do my best to protect your personal information, transmission of personal information to and from my Website is at your own risk. You should only access the Website within a secure environment.

8. DO WE COLLECT INFORMATION FROM MINORS?

In Short: I do not knowingly collect data from or market to children under 18 years of age.

I do not knowingly solicit data from or market to children under 18 years of age. By using the Website, you represent that you are at least 18 or that you are the parent or guardian of such a minor and consent to such minor dependent’s use of the Website. If I learn that personal information from users less than 18 years of age has been collected, I will deactivate the account and take reasonable measures to promptly delete such data from my records. If you become aware of any data I may have collected from children under age 18, please contact me at .

9. WHAT ARE YOUR PRIVACY RIGHTS?

In Short: You may review, change, or terminate your account at any time.

If you are a resident in the European Economic Area and you believe I am unlawfully processing your personal information, you also have the right to complain to your local data protection supervisory authority. You can find their contact details here: http://ec.europa.eu/justice/data-protection/bodies/authorities/index_en.htm.

If you are a resident in Switzerland, the contact details for the data protection authorities are available here: http://ec.europa.eu/justice/data-protection/bodies/authorities/index_en.htm.

Cookies and similar technologies: Most Web browsers are set to accept cookies by default. If you prefer, you can usually choose to set your browser to remove cookies and to reject cookies. If you choose to remove cookies or reject cookies, this could affect certain features or services of my Website.

10. CONTROLS FOR DO-NOT-TRACK FEATURES

Most web browsers and some mobile operating systems and mobile applications include a Do-Not-Track (“DNT”) feature or setting you can activate to signal your privacy preference not to have data about your online browsing activities monitored and collected. At this stage no uniform technology standard for recognizing and implementing DNT signals has been finalized. As such, I do not currently respond to DNT browser signals or any other mechanism that automatically communicates your choice not to be tracked online. If a standard for online tracking is adopted that I must follow in the future, I will inform you about that practice in a revised version of this privacy notice.

11. DO CALIFORNIA RESIDENTS HAVE SPECIFIC PRIVACY RIGHTS?

In Short: Yes, if you are a resident of California, you are granted specific rights regarding access to your personal information.

California Civil Code Section 1798.83, also known as the “Shine The Light” law, permits my users who are California residents to request and obtain from me, once a year and free of charge, information about categories of personal information (if any) I disclosed to third parties for direct marketing purposes and the names and addresses of all third parties with which I shared personal information in the immediately preceding calendar year. If you are a California resident and would like to make such a request, please submit your request in writing to me using the contact information provided below.

If you are under 18 years of age, reside in California, and have a registered account with the Website, you have the right to request removal of unwanted data that you publicly post on the Website. To request removal of such data, please contact us using the contact information provided below, and include the email address associated with your account and a statement that you reside in California. I will make sure the data is not publicly displayed on the Website, but please be aware that the data may not be completely or comprehensively removed from all my systems (e.g. backups, etc.).

12. DO I MAKE UPDATES TO THIS NOTICE?

In Short: Yes, I will update this notice as necessary to stay compliant with relevant laws.

I may update this privacy notice from time to time. The updated version will be indicated by an updated “Revised” date and the updated version will be effective as soon as it is accessible. If I make material changes to this privacy notice, I may notify you either by prominently posting a notice of such changes or by directly sending you a notification. We encourage you to review this privacy notice frequently to be informed of how I am protecting your information.

13. HOW CAN YOU CONTACT ME ABOUT THIS NOTICE?

If you have questions or comments about this notice, you may email me at or by post to:

Kevin C. Pirnie

22 Orlando St.
Feeding Hills, MA 01030
United States of America

14. HOW CAN YOU REVIEW, UPDATE, OR DELETE THE DATA I COLLECT FROM YOU?

Based on the applicable laws of your country, you may have the right to request access to the personal information I collect from you, change that information, or delete it in some circumstances. To request to review, update, or delete your personal information, you may email me at or by post to:

Kevin C. Pirnie

22 Orlando St.
Feeding Hills, MA 01030
United States of America