Blocking problem IPs

I have my contact form set up to throw an exception when a spam attempt is made so now instead of receiving a spam, I receive an exception report.

Exception information:
    Exception type: System.Web.HttpRequestValidationException
    Exception message: A potentially dangerous Request.Form value was detected from the client (message="com1, <a href="http://prof...").

Request information:
    Request path: /Contact
    User host address: 213.5.70.205
    User: 
    Is authenticated: False
    Authentication Type: 
    Thread account name: NT AUTHORITY\\NETWORK SERVICE

It’s always the same two IPs:
User host address: 213.5.70.205
User host address: 188.92.75.82

I’m on shared hosting and don’t have access to IIS control panel. Can I block these IPs without affecting performance for non-spammers?

I’ve got to come up with a better way than just checking against a string because this is only effective against specific IPs and I’m going to need range blocking.

In your web.config…

<system.webServer>
<security>
<ipSecurity>
<add ipAddress="213.5.70.205"/>
<add ipAddress="188.92.75.82"/>
</ipSecurity>
</security>
</system.webServer>

Doesn’t seem to work. Just gives a stock 500 error.

I have no idea so this is just a total shot in the dark. Maybe it takes CIDR format IPs?? eg.
“10.0.0.0/8”,
“172.16.0.0/12”,
“192.168.0.0/16”,

Netmask is an element attribute. And I have no clue why it isn’t working for you. =(

I hardcoded the IPs into an HttpModule to just throw a 403 until I can work out a way to easily update the IP ban list.

On a related note; If I’m using this:

		public void Init(HttpApplication context)
		{
			context.BeginRequest += new EventHandler(Application_BeginRequest);
		}

How often does BeginRequest occur? Will the new eventhandler be run every time a web page is requested? Is there a better way to check once and let it go from there?

You need only to define the Application_BeginRequest method in global.asax.cs .
The BeginRequest event occurs every time a request is made.

Why put it in the global.asax when it’s derived from IHttpModule?

Here is the entire class:

using System;
using System.Web;

namespace DomainModel.Services
{
	public class BlockIPModule : IHttpModule
	{
		public void Dispose() {}

		public void Init(HttpApplication context)
		{
			context.BeginRequest += new EventHandler(Application_BeginRequest);
		}

		private void Application_BeginRequest(object sender, EventArgs e)
		{
			HttpContext context = ((HttpApplication)sender).Context;
			string currentIP = context.Request.UserHostAddress;
			if (!IsIpValid(currentIP))
			{
				context.Response.StatusCode = 403; 
			}
		}

		private bool IsIpValid(string checkIP)
		{
			return (checkIP != "213.5.70.205" && checkIP != "188.92.75.82");
		}

	}
}

What should I use to run this once and then if the user checks out to just give them a pass on further testing? I know it’s not going to take long to run but if I check against a long list of IPs from the database or test against an external blacklist it may slow things down.

Bleh, I’m probably just going to leave it alone unless I get a much larger list of IPs to block.

i think exception occure because some body try html insertion attack on your website. if the problem ip known, you can handle them in code.

It’s just a plain HttpRequestValidationException because someone tried to put a spam link in my contact form. My input is sanitized.

Since the last post there have been zero spam attempts. :smiley: WIN!

I also refactored it a bit to make room for a database table:

using System;
using System.Collections.Generic;
using System.Web;

namespace DomainModel.Services
{
	public class BlockIPModule : IHttpModule
	{
		public void Dispose() { }
		private List<string> badIPs = new List<string> { "213.5.70.205", "188.92.75.82" };

		public void Init(HttpApplication context)
		{
			context.BeginRequest += new EventHandler(Application_BeginRequest);
		}

		private void Application_BeginRequest(object sender, EventArgs e)
		{
			HttpContext context = ((HttpApplication)sender).Context;
			string currentIP = context.Request.UserHostAddress;
			if (!IsIpValid(currentIP))
			{
				context.Response.StatusCode = 403;
			}
		}

		private bool IsIpValid(string checkIP)
		{
			var isValid = !(badIPs.Contains(checkIP));
			return (isValid);
		}

	}
}

Since I don’t want to make any assumptions, I will simply ask…

Is this module really defined in your domainmodel? Considering you might reuse your domain in a desktop app, that module might be rendered useless.

In any case, what I would probably do here is write a service that checks a db table using a repository. Then add a custom attribute in my web project like the following:

public class BlacklistAttribute : AuthorizeAttribute
{
protected override bool AuthorizeCore(HttpContextBase httpContext)
{
 
string userHostAddress = HttpContext.Request.UserHostAddress;
IBlackListService blacklistService = DependencyResolver.Current.GetService<IBlacklistService>();
return !blacklistService.IsBlackListed(userHostAddress) && base.AuthorizeCore(httpContext);
 
}
 
}

Being based on AuthorizeAttribute, you can still use it to check normal things first.


// just check blacklist
[Blacklist]
 
// check roles as well as blacklist
[Blacklist(Roles="Admin")]

And it can be applied anywhere Authorize can, inclusing class level. This allows for a more fine-grained application.

NOTE: Untested code above. You may need to play around with it.

Yes, it’s in my Domain Model Services.

Hmm. Wouldn’t the only IP in a desktop app be 127.0.0.1?

Hey, when did you get “Memeber of the Month”? How awesome is that? :slight_smile:

I use my domain model services to contain items that can be used everywhere but rarely change so they are cached. It works for me. :slight_smile:

Hmm. Wouldn’t the only IP in a desktop app be 127.0.0.1?

Kind of my point.

The semantics of your namespace just confused me because typically, application services aren’t considered part of the “domain”, although it is part of the collective “model”.

Hey, when did you get “Memeber of the Month”? How awesome is that?

Thanks. =)

I guess I don’t get why I’d use an IP block on a desktop app then. :slight_smile:

If I had an answer to this it would probably sound like I was making it all up because I would be. :smiley:

Read the following in it’s entirety, and then ask godaddy if they’ve enabled IP Restrictions. If they have, then use the web.config setup as instructed (includes whole ranges), if not, you might want to think about getting a different host. Restriction by IP is a pretty common thing.

nvm, I lost the link…