diff --git a/mysql-test/r/range.result b/mysql-test/r/range.result
index ae7d0474e2452370718b25c00799175f6c3458a3..6f9b4e41b22fe1d66302cdc1af34e8bcb3af28cb 100644
--- a/mysql-test/r/range.result
+++ b/mysql-test/r/range.result
@@ -720,3 +720,27 @@ id	status
 59	C
 60	C
 DROP TABLE t1;
+CREATE TABLE  t1 (a int, b int, primary key(a,b));
+INSERT INTO  t1 VALUES
+(1,1),(1,2),(1,3),(2,1),(2,2),(2,3),(3,1),(3,2),(3,3),(4,1),(4,2),(4,3);
+CREATE VIEW v1 as SELECT a,b FROM t1 WHERE b=3;
+EXPLAIN SELECT a,b FROM t1 WHERE a < 2 and b=3;
+id	select_type	table	type	possible_keys	key	key_len	ref	rows	Extra
+1	SIMPLE	t1	range	PRIMARY	PRIMARY	4	NULL	4	Using where; Using index
+EXPLAIN SELECT a,b FROM v1 WHERE a < 2 and b=3;
+id	select_type	table	type	possible_keys	key	key_len	ref	rows	Extra
+1	PRIMARY	t1	range	PRIMARY	PRIMARY	4	NULL	4	Using where; Using index
+EXPLAIN SELECT a,b FROM t1 WHERE a < 2;
+id	select_type	table	type	possible_keys	key	key_len	ref	rows	Extra
+1	SIMPLE	t1	range	PRIMARY	PRIMARY	4	NULL	4	Using where; Using index
+EXPLAIN SELECT a,b FROM v1 WHERE a < 2;
+id	select_type	table	type	possible_keys	key	key_len	ref	rows	Extra
+1	PRIMARY	t1	range	PRIMARY	PRIMARY	4	NULL	4	Using where; Using index
+SELECT a,b FROM t1 WHERE a < 2 and b=3;
+a	b
+1	3
+SELECT a,b FROM v1 WHERE a < 2 and b=3;
+a	b
+1	3
+DROP VIEW v1;
+DROP TABLE t1;
diff --git a/mysql-test/t/range.test b/mysql-test/t/range.test
index a285a4b312c68dd4cb1e749aa85e3157dfb048c8..3d2285b16330fea26facfde190e75305aa30645d 100644
--- a/mysql-test/t/range.test
+++ b/mysql-test/t/range.test
@@ -530,3 +530,26 @@ SELECT * FROM t1 WHERE status NOT BETWEEN 'A' AND 'B';
 SELECT * FROM t1 WHERE status < 'A' OR status > 'B';
 
 DROP TABLE t1;
+
+#
+# Test for bug #10031: range to be used over a view
+#
+
+CREATE TABLE  t1 (a int, b int, primary key(a,b));
+
+INSERT INTO  t1 VALUES
+  (1,1),(1,2),(1,3),(2,1),(2,2),(2,3),(3,1),(3,2),(3,3),(4,1),(4,2),(4,3);
+
+CREATE VIEW v1 as SELECT a,b FROM t1 WHERE b=3;
+
+EXPLAIN SELECT a,b FROM t1 WHERE a < 2 and b=3;
+EXPLAIN SELECT a,b FROM v1 WHERE a < 2 and b=3;
+
+EXPLAIN SELECT a,b FROM t1 WHERE a < 2;
+EXPLAIN SELECT a,b FROM v1 WHERE a < 2;
+
+SELECT a,b FROM t1 WHERE a < 2 and b=3;
+SELECT a,b FROM v1 WHERE a < 2 and b=3; 
+
+DROP VIEW v1;
+DROP TABLE t1;
diff --git a/sql/opt_range.cc b/sql/opt_range.cc
index 4c0c895f22aa3cbb3ae5de2860c84f99043954d0..632f1dea3c11b050016fda460f853b7ea30623a6 100644
--- a/sql/opt_range.cc
+++ b/sql/opt_range.cc
@@ -3581,15 +3581,16 @@ static SEL_TREE *get_mm_tree(PARAM *param,COND *cond)
     DBUG_RETURN(ftree);
   }
   default:
-    if (cond_func->arguments()[0]->type() == Item::FIELD_ITEM)
+    if (cond_func->arguments()[0]->real_item()->type() == Item::FIELD_ITEM)
     {
-      field_item= (Item_field*) (cond_func->arguments()[0]);
+      field_item= (Item_field*) (cond_func->arguments()[0]->real_item());
       value= cond_func->arg_count > 1 ? cond_func->arguments()[1] : 0;
     }
     else if (cond_func->have_rev_func() &&
-             cond_func->arguments()[1]->type() == Item::FIELD_ITEM)
+             cond_func->arguments()[1]->real_item()->type() ==
+                                                            Item::FIELD_ITEM)
     {
-      field_item= (Item_field*) (cond_func->arguments()[1]);
+      field_item= (Item_field*) (cond_func->arguments()[1]->real_item());
       value= cond_func->arguments()[0];
     }
     else
@@ -3610,7 +3611,7 @@ static SEL_TREE *get_mm_tree(PARAM *param,COND *cond)
      
   for (uint i= 0; i < cond_func->arg_count; i++)
   {
-    Item *arg= cond_func->arguments()[i];
+    Item *arg= cond_func->arguments()[i]->real_item();
     if (arg != field_item)
       ref_tables|= arg->used_tables();
   }