BUG: fix the bad error raised by HDFStore.put()
State: closed

- [x] closes #34274
- [x] tests added / passed
- [x] passes `black pandas`
- [x] passes `git diff upstream/master -u -- "*.py" | flake8 --diff`
- [x] whatsnew entry
*P.S. something was wrong with `git diff upstream/master` so I directly ran `flake8 ./pandas/io/pytables.py` as it's the only file changed*

------
I was running into the same problem as #34274 and found where the error is. But (as I've just started using pandas for several days:sweet_smile:) I have few knowledge about pandas, so maybe I didn't make the full use of pandas' components.

As seen in #34274, if a `DataFrame` contains non-string elements and is about to be written into an HDF5 file by `HDFStore.put()`, a `TypeError: object of type 'int' has no len()` error is raised.

But it's not the right "error" expected. `HDFStore.put()` can't serialize some types of element, `so report an exception on a column by column basis` is actually needed.

This commit fixes this, now it raises `TypeError: Cannot serialize the column [{column_No}] because its data contents are not string but [{non_string_type}] object dtype` as expected.

Labels:
name: Error Reporting
description: Incorrect or improved errors from pandas
name: IO HDF5
description: read_hdf, HDFStore

Comments:
Hello @1MLightyears! Thanks for updating this PR. We checked the lines you've touched for [PEP 8](https://www.python.org/dev/peps/pep-0008) issues, and found:





There are currently no PEP 8 issues detected in this Pull Request. Cheers! :beers: 

##### Comment last updated at 2021-01-05 00:15:24 UTC
The interesting thing is that in the failed tests (like `Database / Linux_py37_cov (pull_request)`), two of the test case were reported to be wrong, which both include the wrong raised error `"object of type 'int' has no len()"`:
in `pandas\tests\io\pytables\test_store.py`, line `2052~2060`:
```python3
# test append with invalid input to get good error messages

# list in column
df = tm.makeDataFrame()
df["invalid"] = [["a"]] * len(df)
assert df.dtypes["invalid"] == np.object_
msg = re.escape("object of type 'int' has no len()")
with pytest.raises(TypeError, match=msg):
    store.append("df", df)
```
line `2222~2226`:
```python3
with ensure_clean_store(setup_path) as store:
    # this fails because we have a date in the object block......
    msg = "object of type 'int' has no len()"
    with pytest.raises(TypeError, match=msg):
        store.append("df_unimplemented", df)
```
should I change them too?
> The interesting thing is that in the failed tests (like `Database / Linux_py37_cov (pull_request)`), two of the test case were reported to be wrong, which both include the wrong raised error `"object of type 'int' has no len()"`:
> in `pandas\tests\io\pytables\test_store.py`, line `2052~2060`:
> 
> ```python
> # test append with invalid input to get good error messages
> 
> # list in column
> df = tm.makeDataFrame()
> df["invalid"] = [["a"]] * len(df)
> assert df.dtypes["invalid"] == np.object_
> msg = re.escape("object of type 'int' has no len()")
> with pytest.raises(TypeError, match=msg):
>     store.append("df", df)
> ```
> 
> line `2222~2226`:
> 
> ```python
> with ensure_clean_store(setup_path) as store:
>     # this fails because we have a date in the object block......
>     msg = "object of type 'int' has no len()"
>     with pytest.raises(TypeError, match=msg):
>         store.append("df_unimplemented", df)
> ```
> 
> should I change them too?

yes these were wrong in the first place, your change should fix them.

pls also add a whatsnew note (1.3 bug fixes I/O)
Now it's using a new approach to show the error column label, meanwhile keep the interface part as-is.

The test cases is also updated.

And ... as a new comer, actually I don't exactly know what a whatsnew note is 😅  I copied a commit format from `git log` and write my own in commit `99005b8`, if I made that wrong, pls tell me and I'm willing to correct it.

About the two failed test cases, looks like it's involved with HTTP server, and should not be business of the HDF5 I/O part I commit. No idea about it so far.

thanks @1MLightyears