Repository: pandas-dev/pandas

Issue:
read_excel does not raise error with wrong keyword arg
For example:
```python
pd.read_excel('file_name.xlsx',sheet='mysheet')
```
does not raise any error. The right parameter name is "sheetname" . If "sheet" is passed it defaults to the first sheet and no error is raised.
 
sheetname and sheet are very similar and easy to confuse. 

One might think that it is reading the sheet passed as argument when in fact it is another one. 

I would like to suggest for errors to be raised if unexpected args are passed. 












Discussion:
This *may* be little tricky, since IIRC we pass through `**kwargs` to the underlying engine doing the work (though I may be wrong). Can you take a look in `pandas/io/excel.py` to see if there's anything we can do?
@TomAugspurger : You are correct regarding `**kwargs`.  That is indeed quite unfortunate.
Hmm, we could maybe explicitly check for some common mistakes (like `sheet`), verify that none of the engines use them, and raise if we see them? That's fragile to the engines adding them in the future :/
@TomAugspurger : I think we should look into expanding the signature to obviate the need for `**kwargs`.  Ultimately, we would like it to be identical to `read_csv`, but that's another story for another day.
@TomAugspurger: I’m not an experienced programmer, but I could try something. What about something as simple as if parameter passed not in a list of allowed parameters, raise an error?
@lucianoviola : That sounds like a good plan.  Refer to `read_csv` to see which arguments we *can* accept.   Also, use the same error message that you get when you pass in an unexpected argument to a function (i.e. "[function] got an unexpected keyword argument [arg]")
@gfyoung Ok!

Resolving patch:
diff --git a/pandas/io/excel.py b/pandas/io/excel.py
--- a/pandas/io/excel.py
+++ b/pandas/io/excel.py
@@ -303,6 +303,16 @@ def read_excel(io,
                convert_float=True,
                **kwds):
 
+    # Can't use _deprecate_kwarg since sheetname=None has a special meaning
+    if is_integer(sheet_name) and sheet_name == 0 and 'sheetname' in kwds:
+        warnings.warn("The `sheetname` keyword is deprecated, use "
+                      "`sheet_name` instead", FutureWarning, stacklevel=2)
+        sheet_name = kwds.pop("sheetname")
+
+    if 'sheet' in kwds:
+        raise TypeError("read_excel() got an unexpected keyword argument "
+                        "`sheet`")
+
     if not isinstance(io, ExcelFile):
         io = ExcelFile(io, engine=engine)
 


Test patch:
diff --git a/pandas/tests/io/test_excel.py b/pandas/tests/io/test_excel.py
--- a/pandas/tests/io/test_excel.py
+++ b/pandas/tests/io/test_excel.py
@@ -219,6 +219,16 @@ def test_excel_passes_na(self, ext):
                              columns=['Test'])
         tm.assert_frame_equal(parsed, expected)
 
+    def test_deprecated_sheetname(self, ext):
+        # gh-17964
+        excel = self.get_excelfile('test1', ext)
+
+        with tm.assert_produces_warning(FutureWarning, check_stacklevel=False):
+            read_excel(excel, sheetname='Sheet1')
+
+        with pytest.raises(TypeError):
+            read_excel(excel, sheet='Sheet1')
+
     def test_excel_table_sheet_by_index(self, ext):
 
         excel = self.get_excelfile('test1', ext)